1. 程式人生 > >學習筆記隨記-2019-01-01--01

學習筆記隨記-2019-01-01--01

目錄:

*1.學到的知識

*1.1 Mybatis中 的動態SQL模糊查詢

*(1)直接拼接%%

*(2)使用concat函式

*(3)使用 bind 標籤

*1.2.微服務在伺服器執行自動關閉

*2.1.1.本地微服務打成JAR

*1.2.2 nohup 和 & 的區別

*1.2.3 disown

 

1.學到的知識

1.1 Mybatis中 的動態SQL模糊查詢

模糊查詢的多種寫法:

(1)直接拼接%%

如 ‘%’#{name}’%’ 或 “%”#{name}"%",單引號或雙引號都可以。
結合專案中,寫法如下:

 

<where>
    u.`status`=1
    <if test="name != null And name != '%%'">
      AND u.`name` LIKE ('%${name}%')
    </if>
    <if test="roleName != null And name != '%%'">
      AND r.role_name LIKE ('%${roleName}%')
    </if>
</where>

注意:此處不能寫成 “%#{name}%” ,#{name}就成了字串的一部分,會發生這樣一個異常: The error occurred while setting parameters,應該寫成:
"%"#{name}"%",即#{name}是一個整體,前後加上%

 

(2)使用concat函式

使用concat(str1,str2)函式將兩個引數連線

 

<where>
     u.`status`=1
     <if test="name != null" >
       AND u.`name` LIKE CONCAT('%',#{name},'%')
     </if>
     <if test="roleName != null">
       AND r.role_name LIKE CONCAT('%',#{roleName},'%')
     </if>
 </where>

 

(3)使用 bind 標籤

對字串進行繫結,然後對繫結後的字串使用 like 關鍵字進行模糊查詢

 

<where>
       u.`status`=1
       <if test="name != null" >
         <bind name="name" value="'%'+name+'%'"/>
         AND name LIKE #{name}
       </if>
   </where>

Mysql中查詢相關知識拓展:
一般模糊語句如下:
SELECT 欄位 FROM 表 WHERE 某欄位 Like 條件
其中提供了四種匹配模式:

  • 1.%:表示任意0個或多個字元。可匹配任意型別和長度的字元;
  1. _: 表示任意單個字元。匹配單個任意字元,它常用來限定表示式的字元長度語句;

 

  • 3.[ ]:表示括號內所列字元中的一個(類似正則表示式)。指定一個字元、字串或範圍,要求所匹配物件為它們中的任一個;
  • 4.[^ ] :表示不在括號所列之內的單個字元。其取值和 [] 相同,但它要求所匹配物件為指定字元以外的任一個字元。
  • 注意:
  • 查詢內容包含萬用字元時,由於萬用字元的緣故,導致我們查詢特殊字元“%”、“_”、“[”的語句不能正常實現,而把特殊字元用“[ ]”括起便可正常查詢。

疑問1. ${} 與 #{}之間的區別

  • 1.#{} 將傳入的資料當做一個字串,會自動對穿入的資料加一個雙引號。
  • 2.${} 將穿入的資料直接顯示生成在SQL語句中。
  • 3.#{}是預編譯處理,${}是字串替換。
  • 4.Mybatis在處理#{}時,會將sql中的#{}替換為?號,呼叫PreparedStatement的set方法來賦值;

綜上,#{} 能防止SQL注入,${}無法防止注入。
拓展:所謂的SQL注入,也就是通過吧SQL命令插入WEB表單提交或者屬於域名或頁面請求的查詢字串,最終達到欺騙伺服器執行惡意的SQL命令。具體來說,它是利用現有應用程式,將(惡意的)SQL命令注入到後臺資料庫引擎執行的能力。比如:影視網站洩露VIP會員密碼大多就是通過WEB表單遞交查詢字元暴出的。這裡先不深入細說。

對於模糊查詢,高效率寫法:

  • 1.LOCATE
    語法:LOCATE(‘substr’,str,pos)
    說明:
    若pos不存在,返回substr在str中第一次出現的位置,如果substr在str中不存在,返回值為 0 。
    若pos存在,返回substr在str第pos個位置後第一次出現的位置,如果substr在str中不存在,返回值為0。
    模糊查詢,SQL寫法:

 

SELECT `column` FROM `table` WHERE LOCATE('keyword', `field`)>0;

demo:

 

SELECT
  *
FROM
  `user`
WHERE
  LOCATE( 'a', `name` ) > 0

結果如下:

  • 2.POSITION
    語法:POSITION(‘substr’ IN field)
    position可以看做是locate的別名,功能跟locate一樣
    模糊查詢,SQL寫法:

 

SELECT `column` FROM `table` WHERE POSITION('keyword' IN `filed`);

demo:

 

SELECT
  *
FROM
  `user`
WHERE
  POSITION( 'a' IN `name` )

結果如下:

  • 3.INSTR

語法:INSTR(str,‘substr’)
說明:功能跟instr一樣
模糊查詢,SQL寫法:

 

SELECT `column` FROM `table` WHERE INSTR(`field`, 'keyword' )>0;

demo:

 

SELECT
  -
FROM
  `user`
WHERE
  INSTR ( `name`, 'a' )> 0

結果如下:

  • 4.FIND_IN_SET
    語法:FIND_IN_SET(str1,str2)
    說明:返回str2中str1所在的位置索引,其中str2必須以","分割開。
    模糊查詢,SQL寫法:

 

SELECT `column` FROM `table` WHERE FIND_IN_SET('keyword', `filed`);

demo:

 

SELECT
  *
FROM
  `user`
WHERE
  FIND_IN_SET('admin', `name` )

結果如下:

 

1.2.微服務在伺服器執行自動關閉

基於SpringSecurity + Spring OAuth2 + JWT許可權認證的微服務,考慮本地記憶體不夠,想著先將註冊中心 Eurake 和 授權認證中心 UAA-server先放到伺服器上執行,本地單獨執行 資源中心,遠端呼叫授權中心,緩解本地筆記本記憶體不夠的問題。

 

2.1.1.本地微服務打成JAR

將 將註冊中心 Eurak-server 和 授權認證中心 UAA-server 打成可執行Jar包。
在這裡,在伺服器上執行遇到兩個問題,記錄一下問題和解決辦法。

  • (1)使用 java -jar uaa-service-0.0.1-SNAPSHOT.jar & 執行,會將列印資訊顯示在控制檯。
    解決辦法: 將列印的資訊轉移到一個檔案,使用命令如下:
    java -jar uaa-service-0.0.1-SNAPSHOT.jar >uaa.txt &

 

  • (2)使用 java -jar uaa-service-0.0.1-SNAPSHOT.jar >uaa.txt &,會讓微服務自動關閉。
    檢視日誌,發現關閉點資訊如下:
    授權中心 uaa-server 日記記錄:
    2018-12-27 23:03:50.445 [32mINFO [0;39m [34m20823[0;39m — [Thread-9 ] [36mo.s.b.w.s.c.AnnotationConfigServletWebServerApplicationContext [0;39m : Closing org.springframework.boot.web.ser[email protected]704d6e83: startup date [Thu Dec 27 22:09:24 CST 2018]; parent: org.spring[email protected]3ecf72fd

2018-12-27 23:03:50.447 [32mINFO [0;39m [34m20823[0;39m — [Thread-9 ] [36mo.s.c.n.e.serviceregistry.EurekaServiceRegistry [0;39m : Unregistering application uaa-service with eureka with status DOWN

註冊中心,關閉資訊如下:
2018-12-27 23:03:50.465 INFO 20036 — [nio-8761-exec-6] c.n.e.registry.AbstractInstanceRegistry : Registered instance UAA-SERVICE/izwz9ivjuzijxaguw5ni8kz:uaa-service:7777 with status DOWN (replication=false)

2018-12-27 23:03:50.487 INFO 20036 — [ Thread-15] ConfigServletWebServerApplicationContext : Closing org.springframework.boot.web.ser[email protected]60c6f5b: startup date [Thu Dec 27 22:08:45 CST 2018]; parent: org.spring[email protected]66048bfd

2018-12-27 23:03:50.488 INFO 20036 — [ Thread-15] o.s.c.n.e.s.EurekaServiceRegistry : Unregistering application unknown with eureka with status DOWN

找到相關資料,原因是 可執行jar啟動方式的問題:
https://stackoverflow.com/questions/35882496/why-does-my-spring-boot-app-shutdown-by-itself

 

1.2.2 nohup 和 & 的區別

我們知道,當用戶登出(logout)或者網路斷開時,終端會收到 HUP(hangup)訊號從而關閉其所有子程序。因此,我們的解決辦法就有兩種途徑:要麼讓程序忽略 HUP 訊號,要麼讓程序執行在新的會話裡從而成為不屬於此終端的子程序。

所以這就是前面jar在伺服器上執行,只要終端一關閉就會關掉應用程式的問題。

再對下面兩個命令學習下:

  • (1)nohup是永久執行
    執行 nohup --help
    Run COMMAND, ignoring hangup signals. 可以看到是“執行命令,忽略掛起訊號”,然後會發現,nohup執行命令可以使命令永久的執行下去,和使用者終端沒有關係,例如我們斷開SSH連線都不會影響他的執行。
  • (2)&是指在後臺執行
    &是指在後臺執行,但當用戶推出(掛起)的時候,命令自動也跟著退出。
    所以這也就是 退出終端之後,服務會自動關閉的問題。
  • 綜上,永久的在後臺執行的命令為: nohup COMMAN
    使用命令如下:
    java -jar eureka-server-0.0.1-SNAPSHOT.jar >nohup command > eureka.txt 2>&1 &
  • 解析: 2>&1

 

command >out.file 2>&1 &

command>out.file是將command的輸出重定向到out.file檔案,即輸出內容不列印到螢幕上,而是輸出到out.file檔案中。
2>&1 是將標準出錯重定向到標準輸出,這裡的標準輸出已經重定向到了out.file檔案,即將標準出錯也輸出到out.file檔案中。最後一個&, 是讓該命令在後臺執行。
試想2>1代表什麼,2與>結合代表錯誤重定向,而1則代表錯誤重定向到一個檔案1,而不代表標準輸出;換成2>&1,&與1結合就代表標準輸出了,就變成錯誤重定向到標準輸出.

 

1.2.3 disown

場景:
我們已經知道,如果事先在命令前加上 nohup 或者 setsid 就可以避免 HUP 訊號的影響。但是如果我們未加任何處理就已經提交了命令,該如何補救才能讓它避免 HUP 訊號的影響呢?

解決方法:
這時想加 nohup 或者 setsid 已經為時已晚,只能通過作業排程和 disown 來解決這個問題了。讓我們來看一下 disown 的幫助資訊:

disown [-ar] [-h] [jobspec …]

靈活運用 CTRL-z
在我們的日常工作中,我們可以用 CTRL-z 來將當前程序掛起到後臺暫停執行,執行一些別的操作,然後再用 fg 來將掛起的程序重新放回前臺(也可用 bg 來將掛起的程序放在後臺)繼續執行。這樣我們就可以在一個終端內靈活切換執行多個任務,這一點在除錯程式碼時尤為有用。因為將程式碼編輯器掛起到後臺再重新放回時,游標定位仍然停留在上次掛起時的位置,避免了重新定位的麻煩。

用disown -h jobspec來使某個作業忽略HUP訊號。
用disown -ah 來使所有的作業都忽略HUP訊號。
用disown -rh 來使正在執行的作業忽略HUP訊號。
需要注意的是,當使用過 disown 之後,會將把目標作業從作業列表中移除,我們將不能再使用jobs來檢視它,但是依然能夠用ps -ef查詢到它。

但是還有一個問題,這種方法的操作物件是作業,如果我們在執行命令時在結尾加了"&"來使它成為一個作業並在後臺執行,那麼就萬事大吉了,我們可以通過jobs命令來得到所有作業的列表。但是如果並沒有把當前命令作為作業來執行,如何才能得到它的作業號呢?答案就是用 CTRL-z(按住Ctrl鍵的同時按住z鍵)了!

CTRL-z 的用途就是將當前程序掛起(Suspend),然後我們就可以用jobs命令來查詢它的作業號,再用bg jobspec來將它放入後臺並繼續執行。需要注意的是,如果掛起會影響當前程序的執行結果,請慎用此方法。

學習連結:
https://www.ibm.com/developerworks/cn/linux/l-cn-nohup/index.html