Skip to content


CakePHP – Clickatell api for sending sms

I use the clickatell api for sending sms with cakephp. All I did was to grab a php class for the clickatell api which is shown below:

PHP:
  1. class sendsmsComponent extends Object
  2. {
  3.  
  4. var $api_id = "your_clickatell_api_id";
  5. var $user = "your_clickatell_username";
  6. var $password = "you_clickatell_password";
  7. var $use_ssl = false;
  8.  
  9. /**
  10. * Define SMS balance limit below class will not work
  11. * @var integer
  12. */
  13. var $balace_limit = 0;
  14.  
  15. /**
  16. * Gateway command sending method (curl,fopen)
  17. * @var mixed
  18. */
  19. var $sending_method = "fopen";
  20. var $unicode = false;
  21.  
  22. /**
  23. * Optional CURL Proxy
  24. * @var bool
  25. */
  26. var $curl_use_proxy = false;
  27. var $curl_proxy = "http://127.0.0.1:8080";
  28. var $curl_proxyuserpwd = "login:secretpass";
  29.  
  30. /**
  31. * Callback
  32. * 0 - Off
  33. * 1 - Returns only intermediate statuses
  34. * 2 - Returns only final statuses
  35. * 3 - Returns both intermediate and final statuses
  36. * @var integer
  37. */
  38. var $callback = 0;
  39. var $session;
  40. var $batch;
  41.  
  42. /**
  43. * Class constructor
  44. * Create SMS object and authenticate SMS gateway
  45. * @return object New SMS object.
  46. * @access public
  47. */
  48.  
  49. function startup(&$controller)
  50. {
  51. // This method takes a reference to the controller which is loading it.
  52. // Perform controller initialization here.
  53.  
  54. if ($this->use_ssl) {
  55. $this->base            = "http://api.clickatell.com/http";
  56. $this->base_s        = "https://api.clickatell.com/http";
  57. $this->base_batch    = "http://api.clickatell.com/http_batch";
  58. $this->base_s_batch    = "https://api.clickatell.com/http_batch";
  59.  
  60. } else {
  61. $this->base            = "http://api.clickatell.com/http";
  62. $this->base_s        = $this->base;
  63. $this->base_batch   = "http://api.clickatell.com/http_batch";
  64. $this->base_s_batch = $this->base_batch;
  65.  
  66. }
  67. $this->_auth();
  68. }
  69.  
  70. /*
  71. function sms () {
  72. if ($this->use_ssl) {
  73. $this->base   = "http://api.clickatell.com/http";
  74. $this->base_s = "https://api.clickatell.com/http";
  75. } else {
  76. $this->base   = "http://api.clickatell.com/http";
  77. $this->base_s = $this->base;
  78. }
  79. $this->_auth();
  80. }
  81. */
  82.  
  83. /**
  84. * Authenticate SMS gateway
  85. * @return mixed  "OK" or script die
  86. * @access private
  87. */
  88. function _auth() {
  89. $comm = sprintf ("%s/auth?api_id=%s&user=%s&password=%s", $this->base_s, $this->api_id, $this->user, $this->password);
  90. $this->session = $this->_parse_auth ($this->_execgw($comm));
  91. }
  92.  
  93. /**
  94. * Query SMS credis balance
  95. * @return integer  number of SMS credits
  96. * @access public
  97. */
  98. function getbalance() {
  99. $comm = sprintf ("%s/getbalance?session_id=%s", $this->base, $this->session);
  100. return $this->_parse_getbalance ($this->_execgw($comm));
  101. }
  102.  
  103. /**
  104. * Send SMS message
  105. * @param to mixed  The destination address.
  106. * @param from mixed  The source/sender address
  107. * @param text mixed  The text content of the message
  108. * @return mixed  "OK" or script die
  109. * @access public
  110. */
  111. function send($to=null, $from=null, $text=null) {
  112.  
  113. /* Check SMS credits balance */
  114. if ($this->getbalance() <$this->balace_limit) {
  115. die ("You have reach the SMS credit limit!");
  116. };
  117.  
  118. /* Check SMS $text length */
  119. if ($this->unicode == true) {
  120. $this->_chk_mbstring();
  121. if (mb_strlen ($text)> 210) {
  122. die ("Your unicode message is to long! (Current lenght=".mb_strlen ($text).")");
  123. }
  124. /* Does message need to be concatenate */
  125. if (mb_strlen ($text)> 70) {
  126. $concat = "&concat=3";
  127. } else {
  128. $concat = "";
  129. }
  130. } else {
  131. if (strlen ($text)> 465) {
  132. die ("Your message is to long! (Current lenght=".strlen ($text).")");
  133. }
  134. /* Does message need to be concatenate */
  135. if (strlen ($text)> 160) {
  136. $concat = "&concat=3";
  137. } else {
  138. $concat = "";
  139. }
  140. }
  141.  
  142. /* Check $to and $from is not empty */
  143. if (empty ($to)) {
  144. die ("You not specify destination address (TO)!");
  145. }
  146. if (empty ($from)) {
  147. die ("You not specify source address (FROM)!");
  148. }
  149. $from = $this->_custom_encode($from);
  150.  
  151. /* Reformat $to number */
  152. $cleanup_chr = array ("+", " ", "(", ")", "\r", "\n", "\r\n");
  153. $to = str_replace($cleanup_chr, "", $to);
  154.  
  155. /* Send SMS now */
  156. $comm = sprintf ("%s/sendmsg?session_id=%s&to=%s&from=%s&text=%s&callback=%s&unicode=%s%s",
  157. $this->base,
  158. $this->session,
  159. $from,
  160. $this->encode_message($text),
  161. $this->callback,
  162. $this->unicode,
  163. $concat
  164. );
  165. $myvar = $this->_parse_send ($this->_execgw($comm));
  166. return $myvar;
  167. }
  168.  
  169. function sendbatch($to=null, $from=null, $text=null){
  170. /* Check SMS credits balance */
  171. if ($this->getbalance() <$this->balace_limit) {
  172. die ("You have reach the SMS credit limit!");
  173. };
  174.  
  175. /* Check SMS $text length */
  176. if ($this->unicode == true) {
  177. $this->_chk_mbstring();
  178. if (mb_strlen ($text)> 210) {
  179. die ("Your unicode message is to long! (Current lenght=".mb_strlen ($text).")");
  180. }
  181. /* Does message need to be concatenate */
  182. if (mb_strlen ($text)> 70) {
  183. $concat = "&concat=3";
  184. } else {
  185. $concat = "";
  186. }
  187. } else {
  188. if (strlen ($text)> 465) {
  189. die ("Your message is to long! (Current lenght=".strlen ($text).")");
  190. }
  191. /* Does message need to be concatenate */
  192. if (strlen ($text)> 160) {
  193. $concat = "&concat=3";
  194. } else {
  195. $concat = "";
  196. }
  197. }
  198.  
  199. /* Check $to and $from is not empty */
  200. if (empty ($to)) {
  201. die ("You not specify destination address (TO)!");
  202. }
  203. if (empty ($from)) {
  204. die ("You not specify source address (FROM)!");
  205. }
  206. $from = $this->_custom_encode($from);
  207.  
  208. /* get batchID now */
  209. $comm = sprintf ("%s/startbatch?session_id=%s&template=%s&callback=%s&unicode=%s%s",
  210. $this->base_batch,
  211. $this->session,
  212. $this->encode_message($text),
  213. $this->callback,
  214. $this->unicode,
  215. $concat
  216. );
  217. $this->batch = $this->_batchID ($this->_execgw($comm));
  218.  
  219. $comm = sprintf ("%s/quicksend?session_id=%s&batch_id=%s&to=$to&from=$from",
  220. $this->base_batch,
  221. $this->session,
  222. $this->batch
  223. );
  224. $myvar = $this->_parse_sendbatch ($this->_execgw($comm));
  225. return $myvar;
  226. }
  227.  
  228. /**
  229. * Encode message text according to required standard
  230. * @param text mixed  Input text of message.
  231. * @return mixed  Return encoded text of message.
  232. * @access public
  233. */
  234. function encode_message ($text) {
  235. if ($this->unicode != true) {
  236. //standard encoding
  237. //return rawurlencode($text);
  238. return $this->_custom_encode($text);
  239. } else {
  240. //unicode encoding
  241. $uni_text_len = mb_strlen ($text, "UTF-8");
  242. $out_text = "";
  243.  
  244. //encode each character in text
  245. for ($i=0; $i<$uni_text_len; $i++) {
  246. $out_text .= $this->uniord(mb_substr ($text, $i, 1, "UTF-8"));
  247. }
  248.  
  249. return $out_text;
  250. }
  251. }
  252.  
  253. /**
  254. * Unicode function replacement for ord()
  255. * @param c mixed  Unicode character.
  256. * @return mixed  Return HEX value (with leading zero) of unicode character.
  257. * @access public
  258. */
  259. function uniord($c) {
  260. $ud = 0;
  261. if (ord($c{0})>=0 && ord($c{0})<=127)
  262. $ud = ord($c{0});
  263. if (ord($c{0})>=192 && ord($c{0})<=223)
  264. $ud = (ord($c{0})-192)*64 + (ord($c{1})-128);
  265. if (ord($c{0})>=224 && ord($c{0})<=239)
  266. $ud = (ord($c{0})-224)*4096 + (ord($c{1})-128)*64 + (ord($c{2})-128);
  267. if (ord($c{0})>=240 && ord($c{0})<=247)
  268. $ud = (ord($c{0})-240)*262144 + (ord($c{1})-128)*4096 + (ord($c{2})-128)*64 + (ord($c{3})-128);
  269. if (ord($c{0})>=248 && ord($c{0})<=251)
  270. $ud = (ord($c{0})-248)*16777216 + (ord($c{1})-128)*262144 + (ord($c{2})-128)*4096 + (ord($c{3})-128)*64 + (ord($c{4})-128);
  271. if (ord($c{0})>=252 && ord($c{0})<=253)
  272. $ud = (ord($c{0})-252)*1073741824 + (ord($c{1})-128)*16777216 + (ord($c{2})-128)*262144 + (ord($c{3})-128)*4096 + (ord($c{4})-128)*64 + (ord($c{5})-128);
  273. if (ord($c{0})>=254 && ord($c{0})<=255) //error
  274. $ud = false;
  275. return sprintf("%04x", $ud);
  276. }
  277.  
  278. /**
  279. * Spend voucher with sms credits
  280. * @param token mixed  The 16 character voucher number.
  281. * @return mixed  Status code
  282. * @access public
  283. */
  284. function token_pay ($token) {
  285. $comm = sprintf ("%s/http/token_pay?session_id=%s&token=%s",
  286. $this->base,
  287. $this->session,
  288. $token);
  289.  
  290. return $this->_execgw($comm);
  291. }
  292.  
  293. /**
  294. * Execute gateway commands
  295. * @access private
  296. */
  297. function _execgw($command) {
  298. if ($this->sending_method == "curl")
  299. return $this->_curl($command);
  300. if ($this->sending_method == "fopen")
  301. return $this->_fopen($command);
  302. die ("Unsupported sending method!");
  303. }
  304.  
  305. /**
  306. * CURL sending method
  307. * @access private
  308. */
  309. function _curl($command) {
  310. $this->_chk_curl();
  311. $ch = curl_init ($command);
  312. curl_setopt ($ch, CURLOPT_HEADER, 0);
  313. curl_setopt ($ch, CURLOPT_RETURNTRANSFER,1);
  314. curl_setopt ($ch, CURLOPT_SSL_VERIFYPEER,0);
  315. if ($this->curl_use_proxy) {
  316. curl_setopt ($ch, CURLOPT_PROXY, $this->curl_proxy);
  317. curl_setopt ($ch, CURLOPT_PROXYUSERPWD, $this->curl_proxyuserpwd);
  318. }
  319. $result=curl_exec ($ch);
  320. curl_close ($ch);
  321. return $result;
  322. }
  323.  
  324. /**
  325. * fopen sending method
  326. * @access private
  327. */
  328. function _fopen($command) {
  329. $result = '';
  330. $handler = @fopen ($command, 'r');
  331. if ($handler) {
  332. while ($line = @fgets($handler,1024)) {
  333. $result .= $line;
  334. }
  335. fclose ($handler);
  336. return $result;
  337. } else {
  338. die ("Error while executing fopen sending method!
  339. Please check does PHP have OpenSSL support and check does PHP version is greater than 4.3.0.");
  340. }
  341. }
  342.  
  343. /**
  344. * Parse authentication command response text
  345. * @access private
  346. */
  347. function _parse_auth ($result) {
  348. $session = substr($result, 4);
  349. $code = substr($result, 0, 2);
  350. if ($code!="OK") {
  351. return $result;
  352. }
  353. else {
  354. return $session;
  355. }
  356. }
  357.  
  358. /**
  359. * Parse send command response text
  360. * @access private
  361. */
  362. function _parse_send ($result) {
  363. $code = substr($result, 0, 2);
  364. if ($code!="ID") {
  365. //die ("Error sending SMS! ($result)");
  366. return $result;
  367. } else {
  368. $code = "OK";
  369. return $result;
  370. }
  371. }
  372.  
  373. /**
  374. * Parse batchID
  375. * @access private
  376. */
  377. function _batchID ($result) {
  378. $code = substr($result, 0, 2);
  379. $batchID = substr($result,4,33);
  380. if ($code!="ID") {
  381. die ("Error sending SMS! ($result)");
  382. } else {
  383. $code = "OK";
  384. }
  385. return $batchID;
  386. }
  387.  
  388. /**
  389. * Parse batch start response text
  390. * @access private
  391. */
  392. function _parse_sendbatch ($result) {
  393. /*        $code = substr($result, 0, 2);
  394. $batchID = substr($result,4,33);
  395. if ($code!="ID") {
  396. die ("Error sending SMS! ($result)");
  397. } else {
  398. $code = "OK";
  399. }
  400. return $batchID;
  401. */
  402. return $result;
  403. }
  404.  
  405. /**
  406. * Parse getbalance command response text
  407. * @access private
  408. */
  409. function _parse_getbalance ($result) {
  410. $result = substr($result, 8);
  411. return (int)$result;
  412. }
  413.  
  414. /**
  415. * Check for CURL PHP module
  416. * @access private
  417. */
  418. function _chk_curl() {
  419. if (!extension_loaded('curl')) {
  420. die ("This SMS API class can not work without CURL PHP module! Try using fopen sending method.");
  421. }
  422. }
  423.  
  424. /**
  425. * Check for Multibyte String Functions PHP module - mbstring
  426. * @access private
  427. */
  428. function _chk_mbstring() {
  429. if (!extension_loaded('mbstring')) {
  430. die ("Error. This SMS API class is setup to use Multibyte String Functions module - mbstring, but module not found. Please try to set unicode=false in class or install mbstring module into PHP.");
  431. }
  432. }
  433.  
  434. // encode the message so that the
  435. function _custom_encode($text){
  436.  
  437. // numbers and english letters do not need to be encoded
  438. // the following characters are not supported:
  439. // ^ ~ { } [ ] `
  440. // and are replaced as:
  441. // { -> (
  442. // } -> )
  443. // [ -> (
  444. // ] -> )
  445. //
  446. // ~ and ^ are replaced by a space
  447. $trans = array("Α" => "A",
  448. "Ά" => "A",
  449. "Β" => "B",
  450. "Γ"=> "%13",
  451. "Δ"=> "%10",
  452. "Ε"=> "E",
  453. "Έ"=> "E",
  454. "Ζ"=> "Z",
  455. "Η"=> "H",
  456. "Ή"=> "H",
  457. "Θ"=> "%19",
  458. "Ι"=> "I",
  459. "Ί"=> "I",
  460. "Ϊ"=> "I",
  461. "Κ"=> "K",
  462. "Λ"=> "%14",
  463. "Μ"=> "M",
  464. "Ν"=> "N",
  465. "Ξ"=> "%1A",
  466. "Ο"=> "O",
  467. "Ό"=> "O",
  468. "Π"=> "%16",
  469. "Ρ"=> "P",
  470. "Σ"=> "%18",
  471. "Τ"=> "T",
  472. "Υ"=> "Y",
  473. "Ύ"=> "Y",
  474. "Ϋ"=> "Y",
  475. "Φ"=> "%12",
  476. "Χ"=> "X",
  477. "Ψ"=> "%17",
  478. "Ω"=> "%15",
  479. "Ώ"=> "%15",
  480. " "=>urlencode(" "),
  481. "α" => "A",
  482. "ά" => "A",
  483. "β" => "B",
  484. "γ"=> "%13",
  485. "δ"=> "%10",
  486. "ε"=> "E",
  487. "έ"=> "E",
  488. "ζ"=> "Z",
  489. "η"=> "H",
  490. "ή"=> "H",
  491. "θ"=> "%19",
  492. "ι"=> "I",
  493. "ί"=> "I",
  494. "ϊ"=> "I",
  495. "ΐ"=> "I",
  496. "κ"=> "K",
  497. "λ"=> "%14",
  498. "μ"=> "M",
  499. "ν"=> "N",
  500. "ξ"=> "%1A",
  501. "ο"=> "O",
  502. "ό"=> "O",
  503. "π"=> "%16",
  504. "ρ"=> "P",
  505. "σ"=> "%18",
  506. "ς"=> "%18",
  507. "τ"=> "T",
  508. "υ"=> "Y",
  509. "ύ"=> "Y",
  510. "ϋ"=> "Y",
  511. "ΰ"=> "Y",
  512. "φ"=> "%12",
  513. "χ"=> "X",
  514. "ψ"=> "%17",
  515. "ω"=> "%15",
  516. "ώ"=> "%15",
  517. '~'=>'%1B3D',
  518. "!"=>urlencode("!"),
  519. "@"=>urlencode("@"),
  520. "#"=>urlencode("#"),
  521. "$"=>urlencode("$"),
  522. "%"=>urlencode("%"),
  523. '^'=>'%1B14',
  524. "&"=>urlencode("&"),
  525. "*"=>urlencode("*"),
  526. "("=>urlencode("("),
  527. ")"=>urlencode(")"),
  528. "-"=>"-",
  529. "+"=>urlencode("+"),
  530. '`'=>urlencode("'"),
  531. "_"=>"_",
  532. "="=>urlencode("="),
  533. "["=>urlencode("("),
  534. "]"=>urlencode(")"),
  535. ";"=>urlencode(";"),
  536. '{'=>urlencode("("),
  537. '}'=>urlencode(")"),
  538. "|"=>urlencode("|"),
  539. ";"=>urlencode(";"),
  540. ":"=>urlencode(":"),
  541. '"'=>urlencode('"'),
  542. "'"=>urlencode("'"),
  543. "<"=>urlencode("<"),
  544. ">"=>urlencode(">"),
  545. ","=>urlencode(","),
  546. "."=>".",
  547. "?"=>urlencode("?"),
  548. "/"=>urlencode("/"),
  549. //"€"=>urlencode("€")
  550. "€"=>'%1B65'
  551. );
  552.  
  553. $text = strtr($text, $trans);
  554. // convert to uppercase (for english letters that are not translated by the function above)
  555. $text = strtoupper($text);
  556. return $text;
  557. }
  558.  
  559. }

This is a customized class adapted for cakephp and for greek characters, but will work for latin chatacters as well. I dont remember the writer of the original class, if you know who he is, please contact me.

You will need to add this file to this location in your cakephp app folder: controllers/components/sendsms.php

Now, in you sms_controller.php add the following line:

PHP:
  1. var $components = array('Sendsms');

Now, in order to see your remaining credit use the sendsms component in your sms_controller.php like this:

PHP:
  1. function getBalance(){
  2. $balance = $this->Sendsms->getbalance();
  3. $this->set('balance',$balance);
  4. }

or, to dispatch an sms:

PHP:
  1. $results = $this->Sendsms->send($contact_to['Contact']['mobile'],$from,$message);

Posted in cakephp, clickatell, php, sms.


0 Responses

Stay in touch with the conversation, subscribe to the RSS feed for comments on this post.



Some HTML is OK

or, reply to this post via trackback.