api_get.py 7.9 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222
  1. import re
  2. import io
  3. import os
  4. def get_file_list(paths, ext = ".c"):
  5. file_list = []
  6. for path in paths:
  7. for home, _, files in os.walk(path):
  8. for filename in files:
  9. if filename.endswith(ext):
  10. file_list.append(os.path.join(home, filename))
  11. return file_list
  12. #注释的格式:
  13. # /*
  14. # @module 模块的调用名
  15. # @summary 模块的简短描述信息
  16. # @version 版本号,可选
  17. # @data 日期,可选
  18. # */
  19. # /*
  20. # @api/function module.function(调用时用到的完整函数名)
  21. # @string 第一个参数,@后跟参数类型,空格后跟参数解释
  22. # @number[opt=nil] 第二个参数,默认值为nil
  23. # @table[opt={}] 第三个参数,默认值为{}
  24. # ...根据实际,列出所有参数
  25. # @return 类型 返回的第一个值,这里是解释
  26. # @return string 返回的第二个值,类型为string
  27. # ...根据实际,列处所有返回值
  28. # @demo demo路径
  29. # @video 视频链接
  30. # @usage
  31. # --使用的例子,可多行
  32. # lcoal a,b,c = module.function("test",nil,{1,2,3})
  33. # */
  34. # static int l_module_function(lua_State *L) {
  35. # //一堆代码
  36. # }
  37. #
  38. #//@const NONE number 无校验
  39. ########################################################
  40. #数据结构:
  41. # modules = [
  42. # {
  43. # 'module': 'adc',
  44. # 'summary': '数模转换',
  45. # 'url': 'https://xxxxxx',
  46. # 'demo': 'adc',
  47. # 'video': 'https://xxxxx',
  48. # 'usage': '--xxxxxxx',
  49. # 'tag': 'bsp里的tag',
  50. # 'const': [
  51. # {
  52. # 'var':'uart.NONE',
  53. # 'type':'number',
  54. # 'summary':'无校验',
  55. # },
  56. # ],
  57. # 'api':[
  58. # {
  59. # 'api':'adc.read(id)',
  60. # 'summary': '读取adc通道',
  61. # 'tag': 'bsp里的tag',
  62. # 'args': [
  63. # {
  64. # 'type': 'int',
  65. # 'summary': '通道id,与具体设备有关,通常从0开始'
  66. # }
  67. # ],
  68. # 'return': [
  69. # {
  70. # 'type': 'int',
  71. # 'summary': '原始值'
  72. # },
  73. # {
  74. # 'type': 'int',
  75. # 'summary': '计算后的值'
  76. # }
  77. # ],
  78. # 'usage': '-- 打开adc通道2,并读取\nif adc.open(2) then...'
  79. # },
  80. # ]
  81. # }
  82. # ]
  83. def get_modules(file_list, start="/*", end="*/"):
  84. modules = []
  85. for file in file_list:
  86. text = ""
  87. try:
  88. f = io.open(file,"r",encoding="utf-8")
  89. text = f.read()
  90. f.close()
  91. except:
  92. #print("read fail, maybe not use utf8")
  93. continue
  94. module = {}
  95. file = file.replace("\\","/")
  96. if file.rfind("luat/") >= 0:
  97. file = file[file.rfind("luat/"):]
  98. module["url"] = "https://gitee.com/openLuat/LuatOS/tree/master/"+file
  99. else:
  100. module["url"] = ""
  101. # 注释头
  102. r = re.search(re.escape(start) + r" *\n *@module *(\w+)\n *@summary *(.+)\n",text,re.I|re.M)
  103. if r:
  104. module["module"] = r.group(1)
  105. module["summary"] = r.group(2)
  106. module["usage"] = ""
  107. module["demo"] = ""
  108. module["video"] = ""
  109. module["tag"] = ""
  110. module["api"] = []
  111. module["const"] = []
  112. else:
  113. continue
  114. for mstep in range(len(modules)-1,-1,-1):
  115. if modules[mstep]["module"] == module["module"]:
  116. module = modules[mstep]
  117. del modules[mstep]
  118. module["url"] = ""
  119. #后面的数据
  120. lines = text.splitlines()
  121. line_now = 0
  122. isGotApi = False #是否已经有过接口? 或者是否第一段注释已结束?
  123. while line_now<len(lines)-3:
  124. if lines[line_now].find(end) >= 0:
  125. isGotApi = True #第一段注释结束了,不用找例子了
  126. if not isGotApi:#库自带的例子
  127. if re.search(" *@demo *.+",lines[line_now],re.I):
  128. module["demo"] = "https://gitee.com/openLuat/LuatOS/tree/master/demo/"
  129. module["demo"] += re.search(" *@demo * (.+) *",lines[line_now],re.I).group(1)
  130. line_now+=1
  131. continue
  132. if re.search(" *@video *.+",lines[line_now],re.I):
  133. module["video"] = re.search(" *@video * (.+) *",lines[line_now],re.I).group(1)
  134. line_now+=1
  135. continue
  136. if re.search(" *@tag *.+",lines[line_now],re.I):
  137. module["tag"] = re.search(" *@tag * (.+) *",lines[line_now],re.I).group(1)
  138. line_now+=1
  139. continue
  140. if re.search(" *@usage *",lines[line_now],re.I):
  141. line_now+=1
  142. while lines[line_now].find(end) < 0:
  143. module["usage"] += lines[line_now]+"\n"
  144. line_now+=1
  145. isGotApi = True
  146. continue
  147. #匹配api完整名称行
  148. name = re.search(r" *@api *(.+) *",lines[line_now+2],re.I)
  149. if not name:
  150. name = re.search(r" *@function *(.+) *",lines[line_now+2],re.I)
  151. #匹配常量
  152. const_re = re.search(r"[ \-]*//@const +(.+?) +(.+?) +(.+)",lines[line_now],re.I)
  153. if const_re:
  154. const = {}
  155. const["var"] = module["module"]+"."+const_re.group(1)
  156. const["type"] = const_re.group(2)
  157. const["summary"] = const_re.group(3)
  158. module["const"].append(const)
  159. if lines[line_now].startswith(start) and name:
  160. api = {}
  161. api["api"] = name.group(1)
  162. api["summary"] = re.search(r" *(.+) *",lines[line_now+1],re.I).group(1)
  163. api["tag"] = ""
  164. line_now += 3
  165. api["args"] = []
  166. api["return"] = []
  167. api["usage"] = ""
  168. if re.search(" *@tag *.+",lines[line_now],re.I):
  169. api["tag"] = re.search(" *@tag * (.+) *",lines[line_now],re.I).group(1)
  170. line_now+=1
  171. arg_re = r" *@([^ ]+) +(.+) *"
  172. return_re = r" *@return *([^ ]+) +(.+) *"
  173. isGotApi = True
  174. #匹配输入参数
  175. while True:
  176. arg = re.search(arg_re,lines[line_now],re.I)
  177. arg_return = re.search(return_re,lines[line_now],re.I)
  178. if arg and not arg_return:
  179. api["args"].append({'type':arg.group(1),'summary':arg.group(2)})
  180. line_now+=1
  181. else:
  182. break
  183. #匹配返回值
  184. while True:
  185. arg = re.search(return_re,lines[line_now],re.I)
  186. if arg:
  187. api["return"].append({'type':arg.group(1),'summary':arg.group(2)})
  188. line_now+=1
  189. else:
  190. break
  191. #匹配用法例子
  192. while True:
  193. arg = re.search(" *@usage *",lines[line_now],re.I)
  194. if arg:
  195. line_now+=1
  196. while lines[line_now].find(end) < 0:
  197. api["usage"] += lines[line_now]+"\n"
  198. line_now+=1
  199. else:
  200. line_now+=2
  201. break
  202. module["api"].append(api)
  203. else:
  204. line_now += 1
  205. #没有api的包,不导入
  206. if len(module["api"]) > 0:
  207. modules.append(module)
  208. print(module["module"])
  209. #按名字排个序
  210. def sorfFnc(k):
  211. return k["module"]
  212. modules.sort(key=sorfFnc)
  213. return modules