顯示具有 php 標籤的文章。 顯示所有文章
顯示具有 php 標籤的文章。 顯示所有文章

2018年6月13日 星期三

PHP PDO 使用 LIKE 進行模糊搜尋的正確寫法

一般來說 SQL 裡面,要用模糊搜尋,可使用%來當作萬用字元*,例如

$sql = "select * from user where name like '%$name%' ";

但是PDO為了避免被SQL injection攻擊,會把符號自動轉換前後加上拖曳字元等,讓攻擊失效,可是這會造成 LIKE 的語法,解析錯誤,所以正確的PDO寫法為

$name = '%'.$name.'%';
$sql = "select * from user where name like :NAME";
$d = $this->DB->prepare($sql);
$d->bindParam(":NAME", $name);
$d->execute();
$data = $d->fetchAll();

2018年5月31日 星期四

php curl 發送 request payload 資料

一般來說 在網頁上傳輸資料 通常都是用 form 在丟,所以資料 會放在 form data 這個區塊,
但是我這幾天碰到一個神奇的網站,資料是塞在request payload裡面的,爬了好多文才知道該怎麼正確的丟...


$post_data = 'path=down
month=2018/05/31
cnt=1
itemno=22';

$ch = curl_init();
curl_setopt($ch, CURLOPT_URL,$URL);
curl_setopt($ch, CURLOPT_TIMEOUT, 1); //timeout after 30 seconds
curl_setopt($ch, CURLOPT_RETURNTRANSFER,1);
curl_setopt($ch, CURLOPT_HTTPAUTH, CURLAUTH_ANY);
curl_setopt($ch, CURLOPT_USERPWD, "$username:$password"); // basic auth 認證}
curl_setopt($ch, CURLOPT_POST, true);
curl_setopt($ch, CURLOPT_HTTPHEADER, array('Content-Type: application/x-www-form-urlencoded'));
curl_setopt($ch, CURLOPT_POSTFIELDS, $post_data);
$result=curl_exec ($ch);
$status_code = curl_getinfo($ch, CURLINFO_HTTP_CODE);   //get status code
curl_close ($ch);
重點如下

  1. Content-Type 要設為 application/x-www-form-urlencoded 不要被browser的 text/plain 騙了
  2. 超奇琶的變數設定方法,請看上方的$post_data,直接用 path=down這樣設定變數內容,然後如果有多個變數,直接用換行切換,直接用換行切換,直接用換行切換,很重要所以要說三次...

2018年1月31日 星期三

PHP取得名稱含有小數點的POST, GET變數

最近在玩Facebook API,發現Facebook會傳名稱含有小數點的變數過來
如:hub.mode

我用 $_GET[hub.mode] 完全取不到該值,上網google看看大家怎麼寫的,原來PHP會自動把小數點改為底線,所以只要用 $_GET[hub_mode] 就可以取得該值囉

所以只要對方傳來的變數名稱含有小數點,直接改用底線取帶小數點就行囉

例:hub.verify_token => hub_verify_token

2017年9月5日 星期二

PHP使用JOIN時不會按照順序排序的解決方法

剛剛解掉了真是世紀無敵難的一個bug...
原因是因為 我要讓某個array按照某個順序使用join印出來
但是我array的創造方式是
$a[1] = 'b';
$a[2] = 'c';
$a[0] = 'a';
使用join,怎麼用都是印出 b,c,a
後來使用print_r 才看出問題是在 array 的創造方式,
讓array實際長的是 1 > 2 > 0 的順序,
但是使用一般for迴圈又感覺不出來,
最後使用 ksort 排序過一次之後,再使用join問題就解決了...

2017年8月4日 星期五

解決PHP出現 Notice: Undefined variable 的問題

原本PHP是不須宣告變數的,在5.0版左右(?),變成要預先宣告變數,不然會出現成 Notice: Undefined variable 這個Error

解決方式:

  1. 乖乖宣告變數,我就是懶得宣告才會出現這個警告的阿...
  2. php.ini 內的 error_reporting 改成 error_reporting = E_ALL & ~E_NOTICE
使用方法2就能一勞永逸~~~


2016年11月30日 星期三

PHP Warning: Header may not contain more than a single header, new line detected in xxxx.php on line xxx 解決方法

剛剛收到一個回覆,運作很久的程式忽然無法動了,看了一下error log 出現以下錯誤
PHP Warning: Header may not contain more than a single header, new line detected in xxxx.php on line xxx

google了很久,抓不到原因,字面上是說你有太多header在運作,但是我把所有header都刪掉了,只剩一個還是出現這個錯誤,後來終於google到一篇,是因為我用header location進行轉址,但是轉址過去的url變數含有換行符號,所以把換行符號過濾掉即可

$url = preg_replace('/\s+/', '', $url);

參考資料:

2011年1月28日 星期五

php自動打上svn版號

好吧,感覺又是一篇很聳動的標題,其實只是一些小應用,程式在出版的時候總是喜歡給個版號方便做區別,大部分會採用1.0.xx之類的寫法,最前面的1是程式架構有大變動的時候增加,0大概是有小改版時增加,而xx通常都會是svn的版號,因為這可能是最小幅度的更動,svn有自動把某個關鍵字取代為特定字串的功能,例如:更新日期、版號等。今天要交的就是利用svn自動打版號功能,讓php產生出漂亮的版號。

2011年1月27日 星期四

計算php運算時間ms等級

想要計算一個php頁面運算到底要多久可以在程式一開始時呼叫time function,運算結束後再呼叫一次,計算2次的時間差,不過time的等級只到秒,如果算的東西很少,可能得到的結果為0秒


下面程式可以計算頁面運算速度到ms等級

2011年1月19日 星期三

PHP Fatal error: Out of memory 解決方式!!

標題好像下的很聳動 XD

今天在聊天的時候遇到有人跟我聊到他的程式會跑出Out of memory的狀況,明明記憶體已經給很大了,還是會這樣。

我之前也常遇到這個狀況,後來發現是轉換文字編碼的function作怪,只要有用到iconv, mb_xxx,這類的文字編碼function就要小心了,因為這類function非常吃記憶體,我之前估算記憶體用量約為被轉換資料的10倍左右,也就是如果你轉1m的資料,他要跟你要10m的記憶體,如果轉10m他就要100m的記憶體,一般人開給apache的記憶體用量通常不會這麼大,這時就會出錯拉~~~

PHP CLI模式下變數取得方式

什麼是CLI,全名是Command Line Interface,再不懂請自己google。

php不知道多少後開始支援這個,那也不是重點,反正這篇要教的是如何在CLI模式下拿到變數,答案就是使用$argv變數。

在下command line的時候如果是這樣下的
php test.php aa bb cc

2011年1月12日 星期三

在php中使用root權限執行command line指令

php提供了3個function 分別是 system, exec, passthru讓我們可以直接對系統下command指令,這3個function有什麼差別請自己google。

通常php在執行command line指令的時候是取決於apache的權限,所以理論上只要提高apache的權限,就可以了,不過這只是理論上= =",實作的時候不知道為什麼,還是會有權限不足的狀況,明明可以讀寫檔案了,但是要執行某個程式去控制這些檔案的時候還是會出錯,google了很久,找到3種解法。

2011年1月5日 星期三

php function 隱藏參數寫法

我也不知道這東西正式名稱叫什麼XD
反正就是讓你寫的function可以不必每次帶一堆用不到的參數
正常的function寫法是這樣
function test($a,$b,$c){
//do something
}

2010年11月10日 星期三

php上處理utf-16le檔案

最近要在php上讀取excel的檔案,因此有去找一些相關套件以及一些用法,因為要處理的檔案可能會有多國語言問題,所以一開始就規畫要用utf-8來編輯。

1. php excel reader
 這套件讀取excel很方便,但是不支援unicode,失敗。
2. php excel
這套件支援unicode,也不是很複雜,照理說應該用他,不過這東西可能裡面沒寫好,處理個2mb的excel檔,居然要吃掉256mb左右的記憶體,哪來這麼多記憶體給他吃,失敗。

後來就想說不然從CSV格式著手,結果excel輸出CSV不支援unicode,失敗
再來就試輸出成unicode的txt檔案,有成功,沒變亂碼,但是這是utf-16le的編碼,不是utf-8。

我很天真的想說,既然檔案是utf-16le,我以後要輸出的格式也是要utf-16le才能讓excel正確讀取,所以我乾脆整個網站架構改成utf-16le吧,反正瀏覽器支援讀取各式各樣編碼,但帶計膜架甘丹。

因為我採用lamp架構,但是php 5 &mysql 5.5都不支援utf-16,雖然有找出真的能在php上使用utf-16編碼的code,不過只有firefox上能正確顯示,IE上就掛了,所以別天真的想說弄個utf-16架構的網站,這大概只有純html才能辦的到。


確定網站端還是只能用utf-8之後,表示使用者丟utf-16le的檔案上來,我們要轉成utf-8在網站上處理,處理完後再轉成utf-16le回去給他,所以就是要處理utf-8 <=> utf-16le的問題了

上網google了很久,一堆說什麼使用iconv, mb_convert_encoding,utf8_encode,utf16_decode...之類的function,全部失敗,甚至還有人寫一大串在處理0xff, 0xfe之類的東西,但是一樣全部陣亡,根本沒一樣能跑出正常的東西,後來我乾脆把檔案直接用16進位方式打開,直接去看我的程式轉出來的東西跟轉檔程式跑的到底差在哪,看完之後發現檔頭都少人家2個byte,原來是該死的BOM,後來手動在要轉成utf-16的檔案上加上BOM就沒問題了。

只有utf-8允許可以沒有bom,utf-16, utf-32都是一定要有bom的,因為牽涉到little endian跟big endian的問題。
以下是我的code

function utf8_to_utf16($utf8_filename,$utf16_filename){
    $file = fopen($utf8_filename,"r");
    $write = fopen($utf16_filename,"w+");
    if($file){
        $buffer=chr(255).chr(254); //加入BOM
        fwrite($write,$buffer);
        while(($buffer = fgets($file)) != false){
            $buffer=iconv('UTF-8','UTF-16LE',$buffer);
            fwrite($write,$buffer);
        }
    }
}

function utf16_to_utf8($utf16_filename,$utf8_filename){
    $write = fopen($utf8_filename,"w+");
    $buffer=mb_convert_encoding(  file_get_contents( $utf16_filename ), 'UTF-8', 'UTF-16LE' );
    fwrite($write,$buffer);
}
為什麼2種轉法不一樣呢?
因為utf-8轉utf-16時會佔用比較多的記憶體,一次轉的話容易造成記憶體不足,所以分行轉,utf-16就沒這個問題,此外utf-8轉utf-16花的時間也比utf-16轉utf-8多,我測試轉一個12m的檔案,8轉16要花23秒,16轉8只要1秒...

另外,用這個方式轉出來的utf-8是有bom的,要去除的話請自己來 XD

2010年10月27日 星期三

解決header產生的warning: Cannot add header information - headers already sent in...

很早以前我就常用header這個指令來轉頁面,不過使用這個指令有個限制,就是在前面不能輸出任何東西,就算一個空白也不行,不然會出現

 warning: Cannot add header information - headers already sent in...

我一直以為這是個function的限制,就像125cc再怎麼會跑還是不能上高速公路一樣,結果那天一google之後發現,原來他是可以解決的...

只要把php.ini中的output_buffering打開,或者是隨便給個值,就算在header前有任何輸出,也不影響它的功能了,不過要注意的是,我在使用的時候通常是因為程式有錯誤,才會在header前輸出東西,把這功能打開以後,你看不到任何錯誤,因為頁面已經被轉走啦~~~