sessionplus.go 33 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881882883884885886887888889890891892893894895896897898899900901902903904905906907908909910911912913914915916917918919920921922923924925926927928929930931932933934935936937938939940941942943944945946947948949950951952953954955956957958959960961962963964965966967968969970971972973974975976977978979980981982983984985986987988989990991992993994995996997998999100010011002100310041005100610071008100910101011101210131014101510161017101810191020102110221023102410251026102710281029103010311032103310341035103610371038103910401041104210431044104510461047104810491050105110521053105410551056105710581059106010611062106310641065106610671068106910701071107210731074107510761077107810791080108110821083108410851086108710881089109010911092109310941095109610971098109911001101110211031104110511061107110811091110111111121113111411151116111711181119112011211122112311241125112611271128112911301131113211331134113511361137113811391140114111421143114411451146114711481149115011511152115311541155115611571158115911601161116211631164116511661167116811691170117111721173117411751176117711781179118011811182118311841185118611871188118911901191119211931194119511961197119811991200120112021203120412051206120712081209121012111212121312141215121612171218121912201221122212231224122512261227122812291230123112321233123412351236123712381239
  1. // Copyright 2015 The Xorm Authors. All rights reserved.
  2. // Use of this source code is governed by a BSD-style
  3. // license that can be found in the LICENSE file.
  4. package xorm
  5. import (
  6. "database/sql"
  7. "encoding/json"
  8. "errors"
  9. "fmt"
  10. "os"
  11. "reflect"
  12. "regexp"
  13. "strconv"
  14. "strings"
  15. "time"
  16. "github.com/Chronokeeper/anyxml"
  17. "github.com/xormplus/core"
  18. )
  19. type ResultBean struct {
  20. Has bool
  21. Result interface{}
  22. Error error
  23. }
  24. func (resultBean *ResultBean) Json() (bool, string, error) {
  25. if resultBean.Error != nil {
  26. return resultBean.Has, "", resultBean.Error
  27. }
  28. if !resultBean.Has {
  29. return resultBean.Has, "", nil
  30. }
  31. result, err := JSONString(resultBean.Result, true)
  32. return resultBean.Has, result, err
  33. }
  34. func (resultBean *ResultBean) GetResult() (bool, interface{}, error) {
  35. return resultBean.Has, resultBean.Result, resultBean.Error
  36. }
  37. func (session *Session) GetFirst(bean interface{}) *ResultBean {
  38. has, err := session.Get(bean)
  39. r := &ResultBean{Has: has, Result: bean, Error: err}
  40. return r
  41. }
  42. func (resultBean *ResultBean) Xml() (bool, string, error) {
  43. if resultBean.Error != nil {
  44. return false, "", resultBean.Error
  45. }
  46. if !resultBean.Has {
  47. return resultBean.Has, "", nil
  48. }
  49. has, result, err := resultBean.Json()
  50. if err != nil {
  51. return false, "", err
  52. }
  53. if !has {
  54. return has, "", nil
  55. }
  56. var anydata = []byte(result)
  57. var i interface{}
  58. err = json.Unmarshal(anydata, &i)
  59. if err != nil {
  60. return false, "", err
  61. }
  62. resultByte, err := anyxml.Xml(i)
  63. if err != nil {
  64. return false, "", err
  65. }
  66. return resultBean.Has, string(resultByte), err
  67. }
  68. func (resultBean *ResultBean) XmlIndent(prefix string, indent string, recordTag string) (bool, string, error) {
  69. if resultBean.Error != nil {
  70. return false, "", resultBean.Error
  71. }
  72. if !resultBean.Has {
  73. return resultBean.Has, "", nil
  74. }
  75. has, result, err := resultBean.Json()
  76. if err != nil {
  77. return false, "", err
  78. }
  79. if !has {
  80. return has, "", nil
  81. }
  82. var anydata = []byte(result)
  83. var i interface{}
  84. err = json.Unmarshal(anydata, &i)
  85. if err != nil {
  86. return false, "", err
  87. }
  88. resultByte, err := anyxml.XmlIndent(i, prefix, indent, recordTag)
  89. if err != nil {
  90. return false, "", err
  91. }
  92. return resultBean.Has, string(resultByte), err
  93. }
  94. type ResultMap struct {
  95. Results []map[string]interface{}
  96. Error error
  97. }
  98. func (resultMap *ResultMap) List() ([]map[string]interface{}, error) {
  99. return resultMap.Results, resultMap.Error
  100. }
  101. func (resultMap *ResultMap) Count() (int, error) {
  102. if resultMap.Error != nil {
  103. return 0, resultMap.Error
  104. }
  105. if resultMap.Results == nil {
  106. return 0, nil
  107. }
  108. return len(resultMap.Results), nil
  109. }
  110. func (resultMap *ResultMap) ListPage(firstResult int, maxResults int) ([]map[string]interface{}, error) {
  111. if resultMap.Error != nil {
  112. return nil, resultMap.Error
  113. }
  114. if resultMap.Results == nil {
  115. return nil, nil
  116. }
  117. if firstResult >= maxResults {
  118. return nil, ErrParamsFormat
  119. }
  120. if firstResult < 0 {
  121. return nil, ErrParamsFormat
  122. }
  123. if maxResults < 0 {
  124. return nil, ErrParamsFormat
  125. }
  126. if maxResults > len(resultMap.Results) {
  127. return nil, ErrParamsFormat
  128. }
  129. return resultMap.Results[(firstResult - 1):maxResults], resultMap.Error
  130. }
  131. func (resultMap *ResultMap) Json() (string, error) {
  132. if resultMap.Error != nil {
  133. return "", resultMap.Error
  134. }
  135. return JSONString(resultMap.Results, true)
  136. }
  137. func (resultMap *ResultMap) Xml() (string, error) {
  138. if resultMap.Error != nil {
  139. return "", resultMap.Error
  140. }
  141. results, err := anyxml.Xml(resultMap.Results)
  142. if err != nil {
  143. return "", err
  144. }
  145. return string(results), nil
  146. }
  147. func (resultMap *ResultMap) XmlIndent(prefix string, indent string, recordTag string) (string, error) {
  148. if resultMap.Error != nil {
  149. return "", resultMap.Error
  150. }
  151. results, err := anyxml.XmlIndent(resultMap.Results, prefix, indent, recordTag)
  152. if err != nil {
  153. return "", err
  154. }
  155. return string(results), nil
  156. }
  157. func (resultMap *ResultMap) SaveAsCSV(filename string, headers []string, perm os.FileMode) error {
  158. if resultMap.Error != nil {
  159. return resultMap.Error
  160. }
  161. dataset, err := NewDatasetWithData(headers, resultMap.Results)
  162. if err != nil {
  163. return err
  164. }
  165. csv, err := dataset.CSV()
  166. if err != nil {
  167. return err
  168. }
  169. return csv.WriteFile(filename, perm)
  170. }
  171. func (resultMap *ResultMap) SaveAsTSV(filename string, headers []string, perm os.FileMode) error {
  172. if resultMap.Error != nil {
  173. return resultMap.Error
  174. }
  175. dataset, err := NewDatasetWithData(headers, resultMap.Results)
  176. if err != nil {
  177. return err
  178. }
  179. tsv, err := dataset.TSV()
  180. if err != nil {
  181. return err
  182. }
  183. return tsv.WriteFile(filename, perm)
  184. }
  185. func (resultMap *ResultMap) SaveAsHTML(filename string, headers []string, perm os.FileMode) error {
  186. if resultMap.Error != nil {
  187. return resultMap.Error
  188. }
  189. dataset, err := NewDatasetWithData(headers, resultMap.Results)
  190. if err != nil {
  191. return err
  192. }
  193. html := dataset.HTML()
  194. return html.WriteFile(filename, perm)
  195. }
  196. func (resultMap *ResultMap) SaveAsXML(filename string, headers []string, perm os.FileMode) error {
  197. if resultMap.Error != nil {
  198. return resultMap.Error
  199. }
  200. dataset, err := NewDatasetWithData(headers, resultMap.Results)
  201. if err != nil {
  202. return err
  203. }
  204. xml, err := dataset.XML()
  205. if err != nil {
  206. return err
  207. }
  208. return xml.WriteFile(filename, perm)
  209. }
  210. func (resultMap *ResultMap) SaveAsXMLWithTagNamePrefixIndent(tagName string, prifix string, indent string, filename string, headers []string, perm os.FileMode) error {
  211. if resultMap.Error != nil {
  212. return resultMap.Error
  213. }
  214. dataset, err := NewDatasetWithData(headers, resultMap.Results)
  215. if err != nil {
  216. return err
  217. }
  218. xml, err := dataset.XMLWithTagNamePrefixIndent(tagName, prifix, indent)
  219. if err != nil {
  220. return err
  221. }
  222. return xml.WriteFile(filename, perm)
  223. }
  224. func (resultMap *ResultMap) SaveAsYAML(filename string, headers []string, perm os.FileMode) error {
  225. if resultMap.Error != nil {
  226. return resultMap.Error
  227. }
  228. dataset, err := NewDatasetWithData(headers, resultMap.Results)
  229. if err != nil {
  230. return err
  231. }
  232. yaml, err := dataset.YAML()
  233. if err != nil {
  234. return err
  235. }
  236. return yaml.WriteFile(filename, perm)
  237. }
  238. func (resultMap *ResultMap) SaveAsJSON(filename string, headers []string, perm os.FileMode) error {
  239. if resultMap.Error != nil {
  240. return resultMap.Error
  241. }
  242. dataset, err := NewDatasetWithData(headers, resultMap.Results)
  243. if err != nil {
  244. return err
  245. }
  246. json, err := dataset.JSON()
  247. if err != nil {
  248. return err
  249. }
  250. return json.WriteFile(filename, perm)
  251. }
  252. func (resultMap *ResultMap) SaveAsXLSX(filename string, headers []string, perm os.FileMode) error {
  253. if resultMap.Error != nil {
  254. return resultMap.Error
  255. }
  256. dataset, err := NewDatasetWithData(headers, resultMap.Results)
  257. if err != nil {
  258. return err
  259. }
  260. xlsx, err := dataset.XLSX()
  261. if err != nil {
  262. return err
  263. }
  264. return xlsx.WriteFile(filename, perm)
  265. }
  266. type ResultStructs struct {
  267. Result interface{}
  268. Error error
  269. }
  270. func (resultStructs *ResultStructs) Json() (string, error) {
  271. if resultStructs.Error != nil {
  272. return "", resultStructs.Error
  273. }
  274. return JSONString(resultStructs.Result, true)
  275. }
  276. func (resultStructs *ResultStructs) Xml() (string, error) {
  277. if resultStructs.Error != nil {
  278. return "", resultStructs.Error
  279. }
  280. result, err := resultStructs.Json()
  281. if err != nil {
  282. return "", err
  283. }
  284. var anydata = []byte(result)
  285. var i interface{}
  286. err = json.Unmarshal(anydata, &i)
  287. if err != nil {
  288. return "", err
  289. }
  290. resultByte, err := anyxml.Xml(i)
  291. if err != nil {
  292. return "", err
  293. }
  294. return string(resultByte), nil
  295. }
  296. func (resultStructs *ResultStructs) XmlIndent(prefix string, indent string, recordTag string) (string, error) {
  297. if resultStructs.Error != nil {
  298. return "", resultStructs.Error
  299. }
  300. result, err := resultStructs.Json()
  301. if err != nil {
  302. return "", err
  303. }
  304. var anydata = []byte(result)
  305. var i interface{}
  306. err = json.Unmarshal(anydata, &i)
  307. if err != nil {
  308. return "", err
  309. }
  310. resultByte, err := anyxml.XmlIndent(i, prefix, indent, recordTag)
  311. if err != nil {
  312. return "", err
  313. }
  314. return string(resultByte), nil
  315. }
  316. func (session *Session) SqlMapClient(sqlTagName string, args ...interface{}) *Session {
  317. return session.Sql(session.Engine.sqlMap.Sql[sqlTagName], args...)
  318. }
  319. func (session *Session) SqlTemplateClient(sqlTagName string, args ...interface{}) *Session {
  320. map1 := args[0].(map[string]interface{})
  321. if session.Engine.sqlTemplate.Template[sqlTagName] == nil {
  322. return session.Sql("", &map1)
  323. }
  324. sql, err := session.Engine.sqlTemplate.Template[sqlTagName].Execute(map1)
  325. if err != nil {
  326. session.Engine.logger.Error(err)
  327. }
  328. return session.Sql(sql, &map1)
  329. }
  330. func (session *Session) Search(rowsSlicePtr interface{}, condiBean ...interface{}) *ResultStructs {
  331. err := session.Find(rowsSlicePtr, condiBean...)
  332. r := &ResultStructs{Result: rowsSlicePtr, Error: err}
  333. return r
  334. }
  335. // Exec a raw sql and return records as ResultMap
  336. func (session *Session) Query() *ResultMap {
  337. defer session.resetStatement()
  338. if session.IsAutoClose {
  339. defer session.Close()
  340. }
  341. sql := session.Statement.RawSQL
  342. params := session.Statement.RawParams
  343. i := len(params)
  344. var result []map[string]interface{}
  345. var err error
  346. if i == 1 {
  347. vv := reflect.ValueOf(params[0])
  348. if vv.Kind() != reflect.Ptr || vv.Elem().Kind() != reflect.Map {
  349. result, err = session.queryAll(sql, params...)
  350. } else {
  351. result, err = session.queryAllByMap(sql, params[0])
  352. }
  353. } else {
  354. result, err = session.queryAll(sql, params...)
  355. }
  356. r := &ResultMap{Results: result, Error: err}
  357. return r
  358. }
  359. // Exec a raw sql and return records as ResultMap
  360. func (session *Session) QueryWithDateFormat(dateFormat string) *ResultMap {
  361. defer session.resetStatement()
  362. if session.IsAutoClose {
  363. defer session.Close()
  364. }
  365. sql := session.Statement.RawSQL
  366. params := session.Statement.RawParams
  367. i := len(params)
  368. var result []map[string]interface{}
  369. var err error
  370. if i == 1 {
  371. vv := reflect.ValueOf(params[0])
  372. if vv.Kind() != reflect.Ptr || vv.Elem().Kind() != reflect.Map {
  373. result, err = session.queryAllWithDateFormat(dateFormat, sql, params...)
  374. } else {
  375. result, err = session.queryAllByMapWithDateFormat(dateFormat, sql, params[0])
  376. }
  377. } else {
  378. result, err = session.queryAllWithDateFormat(dateFormat, sql, params...)
  379. }
  380. r := &ResultMap{Results: result, Error: err}
  381. return r
  382. }
  383. // Execute raw sql
  384. func (session *Session) Execute() (sql.Result, error) {
  385. defer session.resetStatement()
  386. if session.IsAutoClose {
  387. defer session.Close()
  388. }
  389. sqlStr := session.Statement.RawSQL
  390. params := session.Statement.RawParams
  391. i := len(params)
  392. if i == 1 {
  393. vv := reflect.ValueOf(params[0])
  394. if vv.Kind() != reflect.Ptr || vv.Elem().Kind() != reflect.Map {
  395. return session.exec(sqlStr, params...)
  396. } else {
  397. sqlStr1, args, _ := core.MapToSlice(sqlStr, params[0])
  398. return session.exec(sqlStr1, args...)
  399. }
  400. } else {
  401. return session.exec(sqlStr, params...)
  402. }
  403. }
  404. // =============================
  405. // for Object
  406. // =============================
  407. func (session *Session) queryAll(sqlStr string, paramStr ...interface{}) (resultsSlice []map[string]interface{}, err error) {
  408. session.queryPreprocess(&sqlStr, paramStr...)
  409. if session.IsAutoCommit {
  410. return query3(session.DB(), sqlStr, paramStr...)
  411. }
  412. return txQuery3(session.Tx, sqlStr, paramStr...)
  413. }
  414. func (session *Session) queryAllByMap(sqlStr string, paramMap interface{}) (resultsSlice []map[string]interface{}, err error) {
  415. sqlStr1, param, _ := core.MapToSlice(sqlStr, paramMap)
  416. session.queryPreprocess(&sqlStr1, param...)
  417. if session.IsAutoCommit {
  418. return query3(session.DB(), sqlStr1, param...)
  419. }
  420. return txQuery3(session.Tx, sqlStr1, param...)
  421. }
  422. func (session *Session) queryAllByMapWithDateFormat(dateFormat string, sqlStr string, paramMap interface{}) (resultsSlice []map[string]interface{}, err error) {
  423. sqlStr1, param, _ := core.MapToSlice(sqlStr, paramMap)
  424. session.queryPreprocess(&sqlStr1, param...)
  425. if session.IsAutoCommit {
  426. return query3WithDateFormat(session.DB(), dateFormat, sqlStr1, param...)
  427. }
  428. return txQuery3WithDateFormat(session.Tx, dateFormat, sqlStr1, param...)
  429. }
  430. func (session *Session) queryAllWithDateFormat(dateFormat string, sqlStr string, paramStr ...interface{}) (resultsSlice []map[string]interface{}, err error) {
  431. session.queryPreprocess(&sqlStr, paramStr...)
  432. if session.IsAutoCommit {
  433. return query3WithDateFormat(session.DB(), dateFormat, sqlStr, paramStr...)
  434. }
  435. return txQuery3WithDateFormat(session.Tx, dateFormat, sqlStr, paramStr...)
  436. }
  437. func (session *Session) queryAllToJsonString(sql string, paramStr ...interface{}) (string, error) {
  438. results, err := session.queryAll(sql, paramStr...)
  439. if err != nil {
  440. return "", err
  441. }
  442. return JSONString(results, true)
  443. }
  444. func (session *Session) queryAllToXmlString(sql string, paramStr ...interface{}) (string, error) {
  445. resultMap, err := session.queryAll(sql, paramStr...)
  446. if err != nil {
  447. return "", err
  448. }
  449. results, err := anyxml.Xml(resultMap)
  450. if err != nil {
  451. return "", err
  452. }
  453. return string(results), nil
  454. }
  455. func (session *Session) queryAllToXmlIndentString(sql string, prefix string, indent string, paramStr ...interface{}) (string, error) {
  456. resultSlice, err := session.queryAll(sql, paramStr...)
  457. if err != nil {
  458. return "", err
  459. }
  460. results, err := anyxml.XmlIndent(resultSlice, prefix, indent, "result")
  461. if err != nil {
  462. return "", err
  463. }
  464. return string(results), nil
  465. }
  466. func (session *Session) queryAllToXmlStringWithDateFormat(dateFormat string, sql string, paramStr ...interface{}) (string, error) {
  467. resultSlice, err := session.queryAll(sql, paramStr...)
  468. if err != nil {
  469. return "", err
  470. }
  471. results, err := anyxml.XmlWithDateFormat(dateFormat, resultSlice)
  472. if err != nil {
  473. return "", err
  474. }
  475. return string(results), nil
  476. }
  477. func (session *Session) queryAllToXmlIndentStringWithDateFormat(dateFormat string, sql string, prefix string, indent string, paramStr ...interface{}) (string, error) {
  478. resultSlice, err := session.queryAll(sql, paramStr...)
  479. if err != nil {
  480. return "", err
  481. }
  482. results, err := anyxml.XmlIndentWithDateFormat(dateFormat, resultSlice, prefix, indent, "results")
  483. if err != nil {
  484. return "", err
  485. }
  486. return string(results), nil
  487. }
  488. func (session *Session) queryAllByMapToJsonString(sql string, paramMap interface{}) (string, error) {
  489. results, err := session.queryAllByMap(sql, paramMap)
  490. if err != nil {
  491. return "", err
  492. }
  493. return JSONString(results, true)
  494. }
  495. func (session *Session) queryAllByMapToJsonStringWithDateFormat(dateFormat string, sql string, paramMap interface{}) (string, error) {
  496. results, err := session.queryAllByMapWithDateFormat(dateFormat, sql, paramMap)
  497. if err != nil {
  498. return "", err
  499. }
  500. return JSONString(results, true)
  501. }
  502. func (session *Session) queryAllToJsonStringWithDateFormat(dateFormat string, sql string, paramStr ...interface{}) (string, error) {
  503. results, err := session.queryAllWithDateFormat(dateFormat, sql, paramStr...)
  504. if err != nil {
  505. return "", err
  506. }
  507. return JSONString(results, true)
  508. }
  509. func (session *Session) row2BeanWithDateFormat(dateFormat string, rows *core.Rows, fields []string, fieldsCount int, bean interface{}) error {
  510. dataStruct := rValue(bean)
  511. if dataStruct.Kind() != reflect.Struct {
  512. return errors.New("Expected a pointer to a struct")
  513. }
  514. session.Statement.setRefValue(dataStruct)
  515. return session._row2BeanWithDateFormat(dateFormat, rows, fields, fieldsCount, bean, &dataStruct, session.Statement.RefTable)
  516. }
  517. func (session *Session) _row2BeanWithDateFormat(dateFormat string, rows *core.Rows, fields []string, fieldsCount int, bean interface{}, dataStruct *reflect.Value, table *core.Table) error {
  518. scanResults := make([]interface{}, fieldsCount)
  519. for i := 0; i < len(fields); i++ {
  520. var cell interface{}
  521. scanResults[i] = &cell
  522. }
  523. if err := rows.Scan(scanResults...); err != nil {
  524. return err
  525. }
  526. if b, hasBeforeSet := bean.(BeforeSetProcessor); hasBeforeSet {
  527. for ii, key := range fields {
  528. b.BeforeSet(key, Cell(scanResults[ii].(*interface{})))
  529. }
  530. }
  531. defer func() {
  532. if b, hasAfterSet := bean.(AfterSetProcessor); hasAfterSet {
  533. for ii, key := range fields {
  534. b.AfterSet(key, Cell(scanResults[ii].(*interface{})))
  535. }
  536. }
  537. }()
  538. var tempMap = make(map[string]int)
  539. for ii, key := range fields {
  540. var idx int
  541. var ok bool
  542. var lKey = strings.ToLower(key)
  543. if idx, ok = tempMap[lKey]; !ok {
  544. idx = 0
  545. } else {
  546. idx = idx + 1
  547. }
  548. tempMap[lKey] = idx
  549. if fieldValue := session.getField(dataStruct, key, table, idx); fieldValue != nil {
  550. rawValue := reflect.Indirect(reflect.ValueOf(scanResults[ii]))
  551. // if row is null then ignore
  552. if rawValue.Interface() == nil {
  553. continue
  554. }
  555. if fieldValue.CanAddr() {
  556. if structConvert, ok := fieldValue.Addr().Interface().(core.Conversion); ok {
  557. if data, err := value2Bytes(&rawValue); err == nil {
  558. structConvert.FromDB(data)
  559. } else {
  560. session.Engine.logger.Error(err)
  561. }
  562. continue
  563. }
  564. }
  565. if _, ok := fieldValue.Interface().(core.Conversion); ok {
  566. if data, err := value2Bytes(&rawValue); err == nil {
  567. if fieldValue.Kind() == reflect.Ptr && fieldValue.IsNil() {
  568. fieldValue.Set(reflect.New(fieldValue.Type().Elem()))
  569. }
  570. fieldValue.Interface().(core.Conversion).FromDB(data)
  571. } else {
  572. session.Engine.logger.Error(err)
  573. }
  574. continue
  575. }
  576. rawValueType := reflect.TypeOf(rawValue.Interface())
  577. vv := reflect.ValueOf(rawValue.Interface())
  578. fieldType := fieldValue.Type()
  579. hasAssigned := false
  580. col := table.GetColumnIdx(key, idx)
  581. if col.SQLType.IsJson() {
  582. var bs []byte
  583. if rawValueType.Kind() == reflect.String {
  584. bs = []byte(vv.String())
  585. } else if rawValueType.ConvertibleTo(core.BytesType) {
  586. bs = vv.Bytes()
  587. } else {
  588. return fmt.Errorf("unsupported database data type: %s %v", key, rawValueType.Kind())
  589. }
  590. hasAssigned = true
  591. if len(bs) > 0 {
  592. if fieldValue.CanAddr() {
  593. err := json.Unmarshal(bs, fieldValue.Addr().Interface())
  594. if err != nil {
  595. session.Engine.logger.Error(key, err)
  596. return err
  597. }
  598. } else {
  599. x := reflect.New(fieldType)
  600. err := json.Unmarshal(bs, x.Interface())
  601. if err != nil {
  602. session.Engine.logger.Error(key, err)
  603. return err
  604. }
  605. fieldValue.Set(x.Elem())
  606. }
  607. }
  608. continue
  609. }
  610. switch fieldType.Kind() {
  611. case reflect.Complex64, reflect.Complex128:
  612. // TODO: reimplement this
  613. var bs []byte
  614. if rawValueType.Kind() == reflect.String {
  615. bs = []byte(vv.String())
  616. } else if rawValueType.ConvertibleTo(core.BytesType) {
  617. bs = vv.Bytes()
  618. }
  619. hasAssigned = true
  620. if len(bs) > 0 {
  621. if fieldValue.CanAddr() {
  622. err := json.Unmarshal(bs, fieldValue.Addr().Interface())
  623. if err != nil {
  624. session.Engine.logger.Error(err)
  625. return err
  626. }
  627. } else {
  628. x := reflect.New(fieldType)
  629. err := json.Unmarshal(bs, x.Interface())
  630. if err != nil {
  631. session.Engine.logger.Error(err)
  632. return err
  633. }
  634. fieldValue.Set(x.Elem())
  635. }
  636. }
  637. case reflect.Slice, reflect.Array:
  638. switch rawValueType.Kind() {
  639. case reflect.Slice, reflect.Array:
  640. switch rawValueType.Elem().Kind() {
  641. case reflect.Uint8:
  642. if fieldType.Elem().Kind() == reflect.Uint8 {
  643. hasAssigned = true
  644. fieldValue.Set(vv)
  645. }
  646. }
  647. }
  648. case reflect.String:
  649. if rawValueType.Kind() == reflect.String {
  650. hasAssigned = true
  651. fieldValue.SetString(vv.String())
  652. }
  653. case reflect.Bool:
  654. if rawValueType.Kind() == reflect.Bool {
  655. hasAssigned = true
  656. fieldValue.SetBool(vv.Bool())
  657. }
  658. case reflect.Int, reflect.Int8, reflect.Int16, reflect.Int32, reflect.Int64:
  659. switch rawValueType.Kind() {
  660. case reflect.Int, reflect.Int8, reflect.Int16, reflect.Int32, reflect.Int64:
  661. hasAssigned = true
  662. fieldValue.SetInt(vv.Int())
  663. }
  664. case reflect.Float32, reflect.Float64:
  665. switch rawValueType.Kind() {
  666. case reflect.Float32, reflect.Float64:
  667. hasAssigned = true
  668. fieldValue.SetFloat(vv.Float())
  669. }
  670. case reflect.Uint8, reflect.Uint16, reflect.Uint32, reflect.Uint64, reflect.Uint:
  671. switch rawValueType.Kind() {
  672. case reflect.Uint8, reflect.Uint16, reflect.Uint32, reflect.Uint64, reflect.Uint:
  673. hasAssigned = true
  674. fieldValue.SetUint(vv.Uint())
  675. case reflect.Int, reflect.Int8, reflect.Int16, reflect.Int32, reflect.Int64:
  676. hasAssigned = true
  677. fieldValue.SetUint(uint64(vv.Int()))
  678. }
  679. case reflect.Struct:
  680. if fieldType.ConvertibleTo(core.TimeType) {
  681. if rawValueType == core.TimeType {
  682. hasAssigned = true
  683. t := vv.Convert(core.TimeType).Interface().(time.Time)
  684. z, _ := t.Zone()
  685. if len(z) == 0 || t.Year() == 0 { // !nashtsai! HACK tmp work around for lib/pq doesn't properly time with location
  686. dbTZ := session.Engine.DatabaseTZ
  687. if dbTZ == nil {
  688. dbTZ = time.Local
  689. }
  690. session.Engine.logger.Debugf("empty zone key[%v] : %v | zone: %v | location: %+v\n", key, t, z, *t.Location())
  691. t = time.Date(t.Year(), t.Month(), t.Day(), t.Hour(),
  692. t.Minute(), t.Second(), t.Nanosecond(), dbTZ)
  693. }
  694. // !nashtsai! convert to engine location
  695. var tz *time.Location
  696. if col.TimeZone == nil {
  697. t = t.In(session.Engine.TZLocation)
  698. tz = session.Engine.TZLocation
  699. } else {
  700. t = t.In(col.TimeZone)
  701. tz = col.TimeZone
  702. }
  703. // dateFormat to string
  704. //loc, _ := time.LoadLocation("Local") //重要:获取时区 rawValue.Interface().(time.Time).Format(dateFormat)
  705. t, _ = time.ParseInLocation(dateFormat, t.Format(dateFormat), tz)
  706. fieldValue.Set(reflect.ValueOf(t).Convert(fieldType))
  707. } else if rawValueType == core.IntType || rawValueType == core.Int64Type ||
  708. rawValueType == core.Int32Type {
  709. hasAssigned = true
  710. var tz *time.Location
  711. if col.TimeZone == nil {
  712. tz = session.Engine.TZLocation
  713. } else {
  714. tz = col.TimeZone
  715. }
  716. t := time.Unix(vv.Int(), 0).In(tz)
  717. //vv = reflect.ValueOf(t)
  718. fieldValue.Set(reflect.ValueOf(t).Convert(fieldType))
  719. } else {
  720. if d, ok := vv.Interface().([]uint8); ok {
  721. hasAssigned = true
  722. t, err := session.byte2Time(col, d)
  723. if err != nil {
  724. session.Engine.logger.Error("byte2Time error:", err.Error())
  725. hasAssigned = false
  726. } else {
  727. fieldValue.Set(reflect.ValueOf(t).Convert(fieldType))
  728. }
  729. } else if d, ok := vv.Interface().(string); ok {
  730. hasAssigned = true
  731. t, err := session.str2Time(col, d)
  732. if err != nil {
  733. session.Engine.logger.Error("byte2Time error:", err.Error())
  734. hasAssigned = false
  735. } else {
  736. fieldValue.Set(reflect.ValueOf(t).Convert(fieldType))
  737. }
  738. } else {
  739. panic(fmt.Sprintf("rawValueType is %v, value is %v", rawValueType, vv.Interface()))
  740. }
  741. }
  742. } else if nulVal, ok := fieldValue.Addr().Interface().(sql.Scanner); ok {
  743. // !<winxxp>! 增加支持sql.Scanner接口的结构,如sql.NullString
  744. hasAssigned = true
  745. if err := nulVal.Scan(vv.Interface()); err != nil {
  746. //fmt.Println("sql.Sanner error:", err.Error())
  747. session.Engine.logger.Error("sql.Sanner error:", err.Error())
  748. hasAssigned = false
  749. }
  750. } else if col.SQLType.IsJson() {
  751. if rawValueType.Kind() == reflect.String {
  752. hasAssigned = true
  753. x := reflect.New(fieldType)
  754. if len([]byte(vv.String())) > 0 {
  755. err := json.Unmarshal([]byte(vv.String()), x.Interface())
  756. if err != nil {
  757. session.Engine.logger.Error(err)
  758. return err
  759. }
  760. fieldValue.Set(x.Elem())
  761. }
  762. } else if rawValueType.Kind() == reflect.Slice {
  763. hasAssigned = true
  764. x := reflect.New(fieldType)
  765. if len(vv.Bytes()) > 0 {
  766. err := json.Unmarshal(vv.Bytes(), x.Interface())
  767. if err != nil {
  768. session.Engine.logger.Error(err)
  769. return err
  770. }
  771. fieldValue.Set(x.Elem())
  772. }
  773. }
  774. } else if session.Statement.UseCascade {
  775. table := session.Engine.autoMapType(*fieldValue)
  776. if table != nil {
  777. hasAssigned = true
  778. if len(table.PrimaryKeys) != 1 {
  779. panic("unsupported non or composited primary key cascade")
  780. }
  781. var pk = make(core.PK, len(table.PrimaryKeys))
  782. switch rawValueType.Kind() {
  783. case reflect.Int64:
  784. pk[0] = vv.Int()
  785. case reflect.Int:
  786. pk[0] = int(vv.Int())
  787. case reflect.Int32:
  788. pk[0] = int32(vv.Int())
  789. case reflect.Int16:
  790. pk[0] = int16(vv.Int())
  791. case reflect.Int8:
  792. pk[0] = int8(vv.Int())
  793. case reflect.Uint64:
  794. pk[0] = vv.Uint()
  795. case reflect.Uint:
  796. pk[0] = uint(vv.Uint())
  797. case reflect.Uint32:
  798. pk[0] = uint32(vv.Uint())
  799. case reflect.Uint16:
  800. pk[0] = uint16(vv.Uint())
  801. case reflect.Uint8:
  802. pk[0] = uint8(vv.Uint())
  803. case reflect.String:
  804. pk[0] = vv.String()
  805. case reflect.Slice:
  806. pk[0], _ = strconv.ParseInt(string(rawValue.Interface().([]byte)), 10, 64)
  807. default:
  808. panic(fmt.Sprintf("unsupported primary key type: %v, %v", rawValueType, fieldValue))
  809. }
  810. if !isPKZero(pk) {
  811. // !nashtsai! TODO for hasOne relationship, it's preferred to use join query for eager fetch
  812. // however, also need to consider adding a 'lazy' attribute to xorm tag which allow hasOne
  813. // property to be fetched lazily
  814. structInter := reflect.New(fieldValue.Type())
  815. newsession := session.Engine.NewSession()
  816. defer newsession.Close()
  817. has, err := newsession.Id(pk).NoCascade().Get(structInter.Interface())
  818. if err != nil {
  819. return err
  820. }
  821. if has {
  822. //v := structInter.Elem().Interface()
  823. //fieldValue.Set(reflect.ValueOf(v))
  824. fieldValue.Set(structInter.Elem())
  825. } else {
  826. return errors.New("cascade obj is not exist!")
  827. }
  828. }
  829. } else {
  830. session.Engine.logger.Error("unsupported struct type in Scan: ", fieldValue.Type().String())
  831. }
  832. }
  833. case reflect.Ptr:
  834. // !nashtsai! TODO merge duplicated codes above
  835. //typeStr := fieldType.String()
  836. switch fieldType {
  837. // following types case matching ptr's native type, therefore assign ptr directly
  838. case core.PtrStringType:
  839. if rawValueType.Kind() == reflect.String {
  840. x := vv.String()
  841. hasAssigned = true
  842. fieldValue.Set(reflect.ValueOf(&x))
  843. }
  844. case core.PtrBoolType:
  845. if rawValueType.Kind() == reflect.Bool {
  846. x := vv.Bool()
  847. hasAssigned = true
  848. fieldValue.Set(reflect.ValueOf(&x))
  849. }
  850. case core.PtrTimeType:
  851. if rawValueType == core.PtrTimeType {
  852. hasAssigned = true
  853. var x = rawValue.Interface().(time.Time)
  854. fieldValue.Set(reflect.ValueOf(&x))
  855. }
  856. case core.PtrFloat64Type:
  857. if rawValueType.Kind() == reflect.Float64 {
  858. x := vv.Float()
  859. hasAssigned = true
  860. fieldValue.Set(reflect.ValueOf(&x))
  861. }
  862. case core.PtrUint64Type:
  863. if rawValueType.Kind() == reflect.Int64 {
  864. var x = uint64(vv.Int())
  865. hasAssigned = true
  866. fieldValue.Set(reflect.ValueOf(&x))
  867. }
  868. case core.PtrInt64Type:
  869. if rawValueType.Kind() == reflect.Int64 {
  870. x := vv.Int()
  871. hasAssigned = true
  872. fieldValue.Set(reflect.ValueOf(&x))
  873. }
  874. case core.PtrFloat32Type:
  875. if rawValueType.Kind() == reflect.Float64 {
  876. var x = float32(vv.Float())
  877. hasAssigned = true
  878. fieldValue.Set(reflect.ValueOf(&x))
  879. }
  880. case core.PtrIntType:
  881. if rawValueType.Kind() == reflect.Int64 {
  882. var x = int(vv.Int())
  883. hasAssigned = true
  884. fieldValue.Set(reflect.ValueOf(&x))
  885. }
  886. case core.PtrInt32Type:
  887. if rawValueType.Kind() == reflect.Int64 {
  888. var x = int32(vv.Int())
  889. hasAssigned = true
  890. fieldValue.Set(reflect.ValueOf(&x))
  891. }
  892. case core.PtrInt8Type:
  893. if rawValueType.Kind() == reflect.Int64 {
  894. var x = int8(vv.Int())
  895. hasAssigned = true
  896. fieldValue.Set(reflect.ValueOf(&x))
  897. }
  898. case core.PtrInt16Type:
  899. if rawValueType.Kind() == reflect.Int64 {
  900. var x = int16(vv.Int())
  901. hasAssigned = true
  902. fieldValue.Set(reflect.ValueOf(&x))
  903. }
  904. case core.PtrUintType:
  905. if rawValueType.Kind() == reflect.Int64 {
  906. var x = uint(vv.Int())
  907. hasAssigned = true
  908. fieldValue.Set(reflect.ValueOf(&x))
  909. }
  910. case core.PtrUint32Type:
  911. if rawValueType.Kind() == reflect.Int64 {
  912. var x = uint32(vv.Int())
  913. hasAssigned = true
  914. fieldValue.Set(reflect.ValueOf(&x))
  915. }
  916. case core.Uint8Type:
  917. if rawValueType.Kind() == reflect.Int64 {
  918. var x = uint8(vv.Int())
  919. hasAssigned = true
  920. fieldValue.Set(reflect.ValueOf(&x))
  921. }
  922. case core.Uint16Type:
  923. if rawValueType.Kind() == reflect.Int64 {
  924. var x = uint16(vv.Int())
  925. hasAssigned = true
  926. fieldValue.Set(reflect.ValueOf(&x))
  927. }
  928. case core.Complex64Type:
  929. var x complex64
  930. if len([]byte(vv.String())) > 0 {
  931. err := json.Unmarshal([]byte(vv.String()), &x)
  932. if err != nil {
  933. session.Engine.logger.Error(err)
  934. } else {
  935. fieldValue.Set(reflect.ValueOf(&x))
  936. }
  937. }
  938. hasAssigned = true
  939. case core.Complex128Type:
  940. var x complex128
  941. if len([]byte(vv.String())) > 0 {
  942. err := json.Unmarshal([]byte(vv.String()), &x)
  943. if err != nil {
  944. session.Engine.logger.Error(err)
  945. } else {
  946. fieldValue.Set(reflect.ValueOf(&x))
  947. }
  948. }
  949. hasAssigned = true
  950. } // switch fieldType
  951. // default:
  952. // session.Engine.LogError("unsupported type in Scan: ", reflect.TypeOf(v).String())
  953. } // switch fieldType.Kind()
  954. // !nashtsai! for value can't be assigned directly fallback to convert to []byte then back to value
  955. if !hasAssigned {
  956. data, err := value2Bytes(&rawValue)
  957. if err == nil {
  958. session.bytes2Value(col, fieldValue, data)
  959. } else {
  960. session.Engine.logger.Error(err.Error())
  961. }
  962. }
  963. }
  964. }
  965. return nil
  966. }
  967. func (session *Session) queryPreprocessByMap(sqlStr *string, paramMap interface{}) {
  968. re := regexp.MustCompile(`[?](\w+)`)
  969. query := *sqlStr
  970. names := make(map[string]int)
  971. var i int
  972. query = re.ReplaceAllStringFunc(query, func(src string) string {
  973. names[src[1:]] = i
  974. i += 1
  975. return "?"
  976. })
  977. for _, filter := range session.Engine.dialect.Filters() {
  978. query = filter.Do(query, session.Engine.dialect, session.Statement.RefTable)
  979. }
  980. *sqlStr = query
  981. session.Engine.logSQL(*sqlStr, paramMap)
  982. }
  983. func (session *Session) Sqls(sqls interface{}, parmas ...interface{}) *SqlsExecutor {
  984. sqlsExecutor := new(SqlsExecutor)
  985. switch sqls.(type) {
  986. case string:
  987. sqlsExecutor.sqls = sqls.(string)
  988. case []string:
  989. sqlsExecutor.sqls = sqls.([]string)
  990. case map[string]string:
  991. sqlsExecutor.sqls = sqls.(map[string]string)
  992. default:
  993. sqlsExecutor.sqls = nil
  994. sqlsExecutor.err = ErrParamsType
  995. }
  996. if len(parmas) == 0 {
  997. sqlsExecutor.parmas = nil
  998. }
  999. if len(parmas) > 1 {
  1000. sqlsExecutor.parmas = nil
  1001. sqlsExecutor.err = ErrParamsType
  1002. }
  1003. if len(parmas) == 1 {
  1004. switch parmas[0].(type) {
  1005. case map[string]interface{}:
  1006. sqlsExecutor.parmas = parmas[0].(map[string]interface{})
  1007. case []map[string]interface{}:
  1008. sqlsExecutor.parmas = parmas[0].([]map[string]interface{})
  1009. case map[string]map[string]interface{}:
  1010. sqlsExecutor.parmas = parmas[0].(map[string]map[string]interface{})
  1011. default:
  1012. sqlsExecutor.parmas = nil
  1013. sqlsExecutor.err = ErrParamsType
  1014. }
  1015. }
  1016. sqlsExecutor.session = session
  1017. return sqlsExecutor
  1018. }
  1019. func (session *Session) SqlMapsClient(sqlkeys interface{}, parmas ...interface{}) *SqlMapsExecutor {
  1020. sqlMapsExecutor := new(SqlMapsExecutor)
  1021. switch sqlkeys.(type) {
  1022. case string:
  1023. sqlMapsExecutor.sqlkeys = sqlkeys.(string)
  1024. case []string:
  1025. sqlMapsExecutor.sqlkeys = sqlkeys.([]string)
  1026. case map[string]string:
  1027. sqlMapsExecutor.sqlkeys = sqlkeys.(map[string]string)
  1028. default:
  1029. sqlMapsExecutor.sqlkeys = nil
  1030. sqlMapsExecutor.err = ErrParamsType
  1031. }
  1032. if len(parmas) == 0 {
  1033. sqlMapsExecutor.parmas = nil
  1034. }
  1035. if len(parmas) > 1 {
  1036. sqlMapsExecutor.parmas = nil
  1037. sqlMapsExecutor.err = ErrParamsType
  1038. }
  1039. if len(parmas) == 1 {
  1040. switch parmas[0].(type) {
  1041. case map[string]interface{}:
  1042. sqlMapsExecutor.parmas = parmas[0].(map[string]interface{})
  1043. case []map[string]interface{}:
  1044. sqlMapsExecutor.parmas = parmas[0].([]map[string]interface{})
  1045. case map[string]map[string]interface{}:
  1046. sqlMapsExecutor.parmas = parmas[0].(map[string]map[string]interface{})
  1047. default:
  1048. sqlMapsExecutor.parmas = nil
  1049. sqlMapsExecutor.err = ErrParamsType
  1050. }
  1051. }
  1052. sqlMapsExecutor.session = session
  1053. return sqlMapsExecutor
  1054. }
  1055. func (session *Session) SqlTemplatesClient(sqlkeys interface{}, parmas ...interface{}) *SqlTemplatesExecutor {
  1056. sqlTemplatesExecutor := new(SqlTemplatesExecutor)
  1057. switch sqlkeys.(type) {
  1058. case string:
  1059. sqlTemplatesExecutor.sqlkeys = sqlkeys.(string)
  1060. case []string:
  1061. sqlTemplatesExecutor.sqlkeys = sqlkeys.([]string)
  1062. case map[string]string:
  1063. sqlTemplatesExecutor.sqlkeys = sqlkeys.(map[string]string)
  1064. default:
  1065. sqlTemplatesExecutor.sqlkeys = nil
  1066. sqlTemplatesExecutor.err = ErrParamsType
  1067. }
  1068. if len(parmas) == 0 {
  1069. sqlTemplatesExecutor.parmas = nil
  1070. }
  1071. if len(parmas) > 1 {
  1072. sqlTemplatesExecutor.parmas = nil
  1073. sqlTemplatesExecutor.err = ErrParamsType
  1074. }
  1075. if len(parmas) == 1 {
  1076. switch parmas[0].(type) {
  1077. case map[string]interface{}:
  1078. sqlTemplatesExecutor.parmas = parmas[0].(map[string]interface{})
  1079. case []map[string]interface{}:
  1080. sqlTemplatesExecutor.parmas = parmas[0].([]map[string]interface{})
  1081. case map[string]map[string]interface{}:
  1082. sqlTemplatesExecutor.parmas = parmas[0].(map[string]map[string]interface{})
  1083. default:
  1084. sqlTemplatesExecutor.parmas = nil
  1085. sqlTemplatesExecutor.err = ErrParamsType
  1086. }
  1087. }
  1088. sqlTemplatesExecutor.session = session
  1089. return sqlTemplatesExecutor
  1090. }