luacheck — статический анализатор для Lua

Здесь обсуждается всё, что касается макросов.
User avatar
John Doe
Бюрократ
Posts: 11076
Joined: Wed 27 Apr, 2005 20:42
Has thanked: 11 times
Been thanked: 64 times

luacheck — статический анализатор для Lua

Post by John Doe » Tue 16 Jun, 2015 12:36

Luacheck это статический анализатор для Lua.
Luacheck может обнаруживать разнообразные проблемы, такие как использование неопределенных глобальных переменных, неиспользованные переменные и значения, доступ к неинициализированным переменным, недостижимый код и многое другое.

Для установки модуля необходимо скачать архив luacheck-master.zip, взять оттуда папку luacheck (из luacheck-master\src\ ), и поместить в %FARPROFILE%\Macros\modules.

А ниже предлагаются утилиты для удобной работы с luacheck в фаре (содержимое вложения распаковать куда-нибудь в %FARPROFILE%\Macros\scripts).
  1. luacheck_editor.lua позволяет проверять lua-код в активном редакторе фара.
    Запуск назначен на комбинацию Ctrl-Shift-F7 (только для *.lua;*.moon).
    Найденные ошибки и предупреждения отображаются в виде списка.
    Управление:
  2. luacheck_cmdline.lua запускает luacheck из командной строки, c выводом отчётов в консоль.
    • Установка:
    • Запускать с помощью префикса luacheck, например: luacheck: *.lua
      Синтаксис можно посмотреть запустив без параметров, а более подробно — в документации.
Update:
С версии 1.3 поддерживается также работа с Moonscript (в редакторе)
Attachments
luacheck_scripts-1.3.3.7z
(6.87 KiB) Downloaded 51 times

User avatar
HaRT
Moderator
Posts: 7984
Joined: Tue 30 Aug, 2005 17:21
Location: Санкт-Петербург
Has thanked: 66 times
Been thanked: 97 times

luacheck — статический анализатор для Lua

Post by HaRT » Tue 21 Jun, 2016 13:45

Latest post of the previous page:

John Doe wrote: CODE: [ВЫДЕЛИТЬ ВСЁ] [EXPAND/COLLAPSE] [DOWNLOAD] (LUACHECK_EDITOR.LUA)
Спасибо, вижу, что по нажатию на [b]CtrlH[/b] список фильтруется в соответствии с [b]options_alt.only[/b]. Несколько соображений:
1. Слово alt у меня не вызывает никаких ассоциаций с происходящим, я бы предпочёл раздедение major/minor, primary/secondary, …. Ну или объясните, пожалуйста, как бы это лучше осознать и запомнить.
2. Обнаружился неприятный эффект: если после фильтрации список оказался пуст, то кратковременно показывается сообщение “No warnings” и список уже не открывается (если вдуматься, это и не удивительно), но вот фильтр после этого снимается только перезагрузкой макросов — неудобно. Предлагаю, чтобы при включенной фильтрации список показывался, даже если он пустой.
3. Чтобы короткий/пустой список не создавал иллюзию чистого кода, предлагаю в качестве признака отфильтрованности добавить, например, звёздочку в название меню. (Например, AltHistory так индицирует тип фильтра: от начала или в любом месте строки.)
4. Хорошо бы добавить [b]CtrlH[/b] в подсказку на нижней рамке и в Справку.
Фар есть инструмент, а не нянька. © 2009 DrKnS

User avatar
John Doe
Бюрократ
Posts: 11076
Joined: Wed 27 Apr, 2005 20:42
Has thanked: 11 times
Been thanked: 64 times

luacheck — статический анализатор для Lua

Post by John Doe » Tue 21 Jun, 2016 14:22

HaRT wrote: Слово alt у меня не вызывает никаких ассоциаций с происходящим,
Альтернативный набор опций. Настраивается в начале файла, таблицей options_alt. Если хотите, то можно переименовать (параметр и/или шорткат)
HaRT wrote: после этого снимается только перезагрузкой макросов
Это ошибка, исправил
HaRT wrote: Предлагаю, чтобы при включенной фильтрации список показывался, даже если он пустой.
По сути это не фильтрация, а только лишь использование другого набора опций.

И я тут глянул, чтобы "нормально" показать пустой список потребуется добавить слишком много костылей.

P.S.
Возможно вот этого вам хватит, здесь просто скрывается всё что не начинается на "1", но зато список не закрывается.
Code: [Select all] [Expand/Collapse] [Download] (luacheck_editor_HaRT.lua)
  1. local _NAME,_VER = "luacheck","1.2H"
  2.  
  3. local _forumtopic = "<a href="http://forum.farmanager.com/viewtopic.php?f=15&t=9650" class="postlink">http://forum.farmanager.com/viewtopic.php?f=15&t=9650</a>"
  4.  
  5. local luacheck_min_version,lmv_err_msg = "0.11.0","luacheck version %s or newer expected"
  6.  
  7. -- list options
  8.  
  9. local O = {
  10.  
  11.   MaxHeight = 10,
  12.  
  13.   InitPos   = "Bottom", --Top,Bottom,Center
  14.  
  15.   AutoPos   = true,
  16.  
  17.   --CycleMode = "ping-pong",
  18.  
  19.   --ConvertToAnsi = true,
  20.  
  21. }
  22.  
  23.  
  24.  
  25. -- luacheck options
  26.  
  27. local options = { --<a href="http://luacheck.readthedocs.org/en/0.11.0/config.html" class="postlink">http://luacheck.readthedocs.org/en/0.11.0/config.html</a>
  28.  
  29.   new_read_globals={
  30.  
  31.     "Macro","NoMacro","Event","NoEvent","MenuItem","NoMenuItem","CommandLine","NoCommandLine",
  32.  
  33.   };
  34.  
  35.   new_globals={
  36.  
  37.     "_filename",                    --scripts executed in luamacro via cmdline prefix
  38.  
  39.     "export","IsLuaStateRecreated", --lua plugins
  40.  
  41.   }
  42.  
  43.  
  44.  
  45.   --global=false;
  46.  
  47.   --allow_defined=true;
  48.  
  49.   --allow_defined_top=true;
  50.  
  51.   --unused=false;
  52.  
  53.   --unused_args=false;
  54.  
  55.   --unused_secondaries=false;
  56.  
  57.   --redefined=false;
  58.  
  59.   --<a href="http://luacheck.readthedocs.org/en/0.11.0/cli.html#patterns" class="postlink">http://luacheck.readthedocs.org/en/0.11 ... l#patterns</a>
  60.  
  61.   --ignore={"4../.*"};
  62.  
  63.   --enable={};
  64.  
  65.   --only={};
  66.  
  67. }
  68.  
  69. local only_globals
  70.  
  71.  
  72.  
  73. local function showHelp()
  74.  
  75.   if far.Message([[
  76.  
  77. Основные действия:
  78.  
  79. • Enter           - перейти к позиции предупреждения
  80.  
  81. • Esc             - закрыть список и восстановить исходную позицию
  82.  
  83.  
  84.  
  85. Дополнительные действия (не закрывают список):
  86.  
  87. • Ctrl-PgUp       - перейти к позиции, на которую ссылается предупреждение
  88.  
  89. • Ctrl-Up/Down    - скроллировать текст редактора
  90.  
  91.  
  92.  
  93. Управление расположением списка:
  94.  
  95. • Ctrl-Home, Num7 - вверху
  96.  
  97. • Ctrl-End,  Num1 - внизу
  98.  
  99. • Num4            - по центру
  100.  
  101. • F6, Divide      - перебор режимов
  102.  
  103. • F5, Num5        - максимизация
  104.  
  105.  
  106.  
  107. Действия с закладками
  108.  
  109. • Ctrl-0..9       - перейти к позиции закладки 0..9
  110.  
  111. • Ctrl-Shift-0..9 - установить закладку 0..9 в текущей позиции
  112.  
  113. • Add             - добавить сессионную закладку с текущей позицией]],
  114.  
  115. ("%s v%s"):format(_NAME,_VER),"OK;Go to forum;","l")==2 then win.ShellExecute(nil,"open",_forumtopic) end
  116.  
  117. end
  118.  
  119. --todo
  120.  
  121. --• Ctrl-Shift-Enter,
  122.  
  123. --  Ctrl-Enter      - перейти к позиции предупреждения
  124.  
  125. --• Shift-Up,  Num2 - перейти к предыдущему предупреждению
  126.  
  127. --• Shift-Down,Num8 - перейти к следующему предупреждению
  128.  
  129.  
  130.  
  131. local luacheck = require "luacheck"
  132.  
  133. if luacheck._VERSION<luacheck_min_version then error(lmv_err_msg:format(luacheck_min_version)) end
  134.  
  135.  
  136.  
  137. local function MessagePopup(msg,title,flags,delay)
  138.  
  139.   local s = far.SaveScreen()
  140.  
  141.   far.Message(msg,title or "","",flags)
  142.  
  143.   win.Sleep(delay or 500); far.RestoreScreen(s)
  144.  
  145. end
  146.  
  147.  
  148.  
  149. local Id = "CFD31C22-0D17-4D87-829A-14561B529D34"
  150.  
  151. local function expandBreakKeys(BreakKeysArr)
  152.  
  153.   local newBreakKeysArr = {}
  154.  
  155.   for _,item in ipairs(BreakKeysArr) do
  156.  
  157.     if item then
  158.  
  159.       for key in item.BreakKey:gmatch("%S+") do
  160.  
  161.         local newitem = {}
  162.  
  163.         for k,v in pairs(item) do newitem[k]=v end
  164.  
  165.         newitem.BreakKey = key
  166.  
  167.         table.insert(newBreakKeysArr,newitem)
  168.  
  169.       end
  170.  
  171.     end
  172.  
  173.   end
  174.  
  175.   return newBreakKeysArr
  176.  
  177. end
  178.  
  179.  
  180.  
  181. local function setEditorPos(info) editor.SetPosition(nil,info); editor.Redraw() end
  182.  
  183.  
  184.  
  185. local bak_pos
  186.  
  187. local function restorePos()
  188.  
  189.   if bak_pos then
  190.  
  191.     editor.Select(nil,bak_pos)
  192.  
  193.     setEditorPos(bak_pos)
  194.  
  195.   end
  196.  
  197. end
  198.  
  199.  
  200.  
  201. local function scrollEditor(dir)
  202.  
  203.   local ei = editor.GetInfo()
  204.  
  205.   ei.TopScreenLine = ei.TopScreenLine+dir
  206.  
  207.   if ei.TopScreenLine<1 or ei.TopScreenLine>ei.TotalLines-ei.WindowSizeY+1 then mf.beep(); return end
  208.  
  209.   if ei.CurLine-ei.TopScreenLine-(dir==1 and -1 or ei.WindowSizeY)==0 then
  210.  
  211.     ei.CurLine = ei.CurLine+dir
  212.  
  213.   end
  214.  
  215.   setEditorPos(ei)
  216.  
  217. end
  218.  
  219.  
  220.  
  221. local F = far.Flags
  222.  
  223.  
  224.  
  225. local list = {}
  226.  
  227. function list:calcProps(Items,Props)
  228.  
  229.   self.Pos = self.Pos or O.InitPos
  230.  
  231.   Items = assert(Items or self.Items,"Items not set")
  232.  
  233.   local nItems = #Items
  234.  
  235.   Props = assert(Props or self.Props,"Props not set")
  236.  
  237.   -- calculate required list's dimensions and position
  238.  
  239.   local r = far.AdvControl(F.ACTL_GETFARRECT)
  240.  
  241.   local xSize,ySize = r.Right-r.Left,r.Bottom-r.Top --Far size
  242.  
  243.   local MaxItems = ySize-3 --max items n to fit
  244.  
  245.   local X,Y
  246.  
  247.   X = Items.maxlen<xSize-4 and (xSize-Items.maxlen)/2-2 or -1
  248.  
  249.   local nLines = math.min(nItems,O.MaxHeight,MaxItems) --actual list lines n
  250.  
  251.   local Pos = self.Pos or O.InitPos
  252.  
  253.   local isMaximizable = nItems>nLines and nLines<MaxItems
  254.  
  255.   local isMaximized = self.isMaximized and isMaximizable
  256.  
  257.   if Pos=="Center" or isMaximized then
  258.  
  259.     X,Y = -1,-1
  260.  
  261.   elseif Pos=="Top" then
  262.  
  263.     Y = 0
  264.  
  265.   elseif Pos=="Bottom" then
  266.  
  267.     Y = MaxItems-nLines>0 and MaxItems-nLines+1+1 or -1
  268.  
  269.   end
  270.  
  271.   -- set properties
  272.  
  273.   Props.X,Props.Y,Props.MaxHeight = X,Y,isMaximized and 0 or O.MaxHeight
  274.  
  275.   self.Props,self.Items,self.nItems = Props,Items,nItems
  276.  
  277.   self.nLines,self.isMaximized = nLines,isMaximized
  278.  
  279.   self.EditorShiftTop = Far.GetConfig"Editor.ShowTitleBar" and 0 or 1
  280.  
  281.   self.EditorShiftBottom = Far.KeyBar_Show()-1
  282.  
  283. end
  284.  
  285. function list:maximize(state)
  286.  
  287.   self.isMaximized = state==nil and not self.isMaximized or state
  288.  
  289.   self:calcProps()
  290.  
  291. end
  292.  
  293. function list:setPos(Pos)
  294.  
  295.   if Pos==self.Pos then
  296.  
  297.     return list:maximize()
  298.  
  299.   elseif Pos=="ping-pong" then
  300.  
  301.     if self.Pos=="Center" then
  302.  
  303.       Pos = self.prevPos=="Top" and "Bottom" or "Top"
  304.  
  305.     else
  306.  
  307.       Pos = "Center"
  308.  
  309.     end
  310.  
  311.   elseif not Pos then
  312.  
  313.     local next = {["Top"]="Bottom",["Bottom"]="Center",["Center"]="Top"}
  314.  
  315.     Pos = next[self.Pos]
  316.  
  317.   end
  318.  
  319.   self.prevPos = Pos~="Center" and Pos or self.prevPos
  320.  
  321.   self.Pos = Pos
  322.  
  323.   self.isMaximized = false
  324.  
  325.   self:calcProps()
  326.  
  327. end
  328.  
  329. function list:gotoWarning(pos,to_prev,force_top)
  330.  
  331.   local w = self.Items[pos]
  332.  
  333.   local line = to_prev and w.prev_line or w.line
  334.  
  335.   if not line then return end
  336.  
  337.   local column = to_prev and w.prev_column or w.column
  338.  
  339.   local end_column = not to_prev and w.end_column
  340.  
  341.   --select
  342.  
  343.   local width
  344.  
  345.   if end_column then
  346.  
  347.     width = end_column-column+1
  348.  
  349.   elseif w.name then
  350.  
  351.     width = w.name:len()
  352.  
  353.   else
  354.  
  355.     local str = editor.GetString(nil,line)
  356.  
  357.     if not str then return end
  358.  
  359.     local a,b = str.StringText:find("^%S+",column)
  360.  
  361.     width = a and b-a+1 or str.StringLength-column+1
  362.  
  363.   end
  364.  
  365.   editor.Select(nil,F.BTYPE_STREAM,line,column,width,1)
  366.  
  367.   --goto
  368.  
  369.   local nLines,TopScreenLine = self.nLines
  370.  
  371.   if nLines then --trying to correct TopScreenLine in order not to let cursor be hidden behind list
  372.  
  373.     local ei = editor.GetInfo()
  374.  
  375.     local y = line-ei.TopScreenLine --calculated screen line of warning
  376.  
  377.     local a,b = 0,ei.WindowSizeY    --valid screen lines (a..b)
  378.  
  379.     if self.Pos=="Top" then
  380.  
  381.       a = a+nLines+3+self.EditorShiftTop
  382.  
  383.     elseif self.Pos=="Bottom" then
  384.  
  385.       b = b-nLines-4+1+self.EditorShiftBottom
  386.  
  387.     end
  388.  
  389.     TopScreenLine = (y<a or force_top) and math.max(line-a,1)
  390.  
  391.                  or (y>b)              and line-b
  392.  
  393.     --win.OutputDebugString(("%s…%s = %s = %s"):format(a,b,y,TopScreenLine or '-'))
  394.  
  395.   end
  396.  
  397.   setEditorPos{CurLine=line,CurPos=column,TopScreenLine=TopScreenLine}
  398.  
  399. end
  400.  
  401. function list:Up(pos)   return pos-1>=1 and pos-1 or self.nItems end
  402.  
  403. function list:Down(pos) return pos+1<=self.nItems and pos+1 or 1 end
  404.  
  405. local function go(dir,pos,autopos)
  406.  
  407.   local nextpos = list[dir](list,pos)
  408.  
  409.   if autopos then list:gotoWarning(nextpos) end
  410.  
  411.   return nextpos
  412.  
  413. end
  414.  
  415.  
  416.  
  417. local Check --fw decl
  418.  
  419. local bKeys = expandBreakKeys {
  420.  
  421.   {BreakKey="C+UP   C+NUMPAD8 C+8",action=function() scrollEditor(-1) end},
  422.  
  423.   {BreakKey="C+DOWN C+NUMPAD2 C+2",action=function() scrollEditor(1) end},
  424.  
  425.   {BreakKey="C+RETURN C+NEXT C+NUMPAD3 C+3",action=function(pos) list:gotoWarning(pos) end},
  426.  
  427.   {BreakKey="CS+RETURN",        action=function(pos) list:gotoWarning(pos,nil,true) end},
  428.  
  429.   {BreakKey="RETURN",           action=function(pos)
  430.  
  431.      if list.Props.SelectIndex~=pos then list:gotoWarning(pos) end
  432.  
  433.      return "break"
  434.  
  435.    end},
  436.  
  437.   {BreakKey="ESCAPE",           action=function() restorePos(); return "break" end},
  438.  
  439.   {BreakKey="C+PRIOR C+NUMPAD9 C+9",action=function(pos) list:gotoWarning(pos,true) end},
  440.  
  441.   {BreakKey="C+HOME NUMPAD7 7", action=function() list:setPos("Top") end},
  442.  
  443.   {BreakKey="C+END  NUMPAD1 1", action=function() list:setPos("Bottom") end},
  444.  
  445.   {BreakKey="NUMPAD4 4",        action=function() list:setPos("Center") end},
  446.  
  447.   {BreakKey="F6 DIVIDE",        action=function() list:setPos(O.CycleMode) end},
  448.  
  449.   {BreakKey="F5 CLEAR 5",       action=function() list:maximize() end},
  450.  
  451.   {BreakKey="ADD",              action=function() editor.AddSessionBookmark() end},
  452.  
  453.   {BreakKey="CS+1 CS+2 CS+3 CS+4 CS+5 CS+6 CS+7 CS+8 CS+9 CS+0 C+1 C+2 C+3 C+4 C+5 C+6 C+7 C+8 C+9 C+0",keys=true},
  454.  
  455.   {BreakKey="F1",               action=showHelp},
  456.  
  457.   --<a href="http://bugs.farmanager.com/view.php?id=1301#c12736" class="postlink">http://bugs.farmanager.com/view.php?id=1301#c12736</a>
  458.  
  459.   {BreakKey="UP",               action=function(pos) return go("Up",pos,O.AutoPos) end},
  460.  
  461.   {BreakKey="S+UP NUMPAD8 8",   action=function(pos) return go("Up",pos,not O.AutoPos) end},
  462.  
  463.   {BreakKey="DOWN",             action=function(pos) return go("Down",pos,O.AutoPos) end},
  464.  
  465.   {BreakKey="S+DOWN NUMPAD2 2", action=function(pos) return go("Down",pos,not O.AutoPos) end},
  466.  
  467.   --{BreakKey="F3",               action=function(pos) require"le"(list.Items[pos],"Event") end},
  468.  
  469.   --{BreakKey="F9",               action=function() require"le"(O,"Options");list:calcProps() end},
  470.  
  471.   {BreakKey="C+H",              action=function(_,Items)
  472.  
  473.      only_globals = not only_globals
  474.  
  475.      for i=1,#Items do
  476.  
  477.        local item = Items<span style="font-style: italic">
  478.  
  479.        item.hidden = only_globals and item.code and item.code:sub(1,1)~="1"
  480.  
  481.      end
  482.  
  483.    end},
  484.  
  485. }
  486.  
  487.  
  488.  
  489. local Props = {
  490.  
  491.   Title=_NAME;
  492.  
  493.   Bottom="Ctrl-Enter, Ctrl-Up/Down, F5, F6, F1";
  494.  
  495.   Id=win.Uuid(Id);
  496.  
  497. }
  498.  
  499.  
  500.  
  501. function Check()
  502.  
  503.   local ei = editor.GetInfo()
  504.  
  505.   local sel = editor.GetSelection()
  506.  
  507.   if sel then --save for further restoring
  508.  
  509.     ei.BlockStartPos = sel.StartPos
  510.  
  511.     ei.BlockWidth = sel.EndPos-sel.StartPos+1
  512.  
  513.     ei.BlockHeight = sel.EndLine-sel.StartLine+1
  514.  
  515.   end
  516.  
  517.   bak_pos = ei
  518.  
  519.   local source = {}
  520.  
  521.   for i=1,ei.TotalLines do source<span style="font-style: italic"> = editor.GetString(nil,i).StringText end
  522.  
  523.   local text = table.concat(source,"\n")
  524.  
  525.   if O.ConvertToAnsi then
  526.  
  527.     text = win.WideCharToMultiByte(win.Utf8ToUtf16(text),win.GetACP())
  528.  
  529.   end
  530.  
  531.   local report = luacheck.check_strings({text}, options)[1]
  532.  
  533.   if not report then
  534.  
  535.     far.Message("Internal error: unable to get report",_NAME,nil,"w")
  536.  
  537.     return
  538.  
  539.   end
  540.  
  541.   if #report==0 then
  542.  
  543.     MessagePopup("No warnings",_NAME)
  544.  
  545.   else -- proceed with warnings list
  546.  
  547.     local Items,pos,maxlen,err = {},nil,0
  548.  
  549.     for i,w in ipairs(report) do
  550.  
  551.       err = w.code:sub(1,1)=="0"
  552.  
  553.       w.text =  ("%4u:%-3u "):format(w.line,w.column)..
  554.  
  555.                 ("│ %s%s │ "):format(err and "E" or "W",w.code)..
  556.  
  557.                 luacheck.get_message(w)
  558.  
  559.       local len = w.text:len()
  560.  
  561.       maxlen = len>maxlen and len or maxlen
  562.  
  563.       w.checked = err and "‼" or w.code:sub(1,1)=="1" and "!" --[[??]] or w.secondary and "²"
  564.  
  565.       if not pos and w.line==ei.CurLine and w.column==ei.CurPos then pos = i end
  566.  
  567.       Items<span style="font-style: italic"> = w
  568.  
  569.       if not w.end_column then mf.beep() end--??
  570.  
  571.     end
  572.  
  573.     Items.maxlen = maxlen
  574.  
  575.     if err then mf.beep(); mf.postmacro(MessagePopup,"Errors found!",_NAME,"w",300) end
  576.  
  577.     list:calcProps(Items,Props)
  578.  
  579.     if O.AutoPos then list:gotoWarning(pos or 1) end
  580.  
  581.     repeat --todo use dialog instead of menu
  582.  
  583.       -- show list
  584.  
  585.       Props.SelectIndex = pos
  586.  
  587.       local item
  588.  
  589.       item,pos = far.Menu(Props,Items,bKeys)
  590.  
  591.       -- process breakkeys
  592.  
  593.       if not item then
  594.  
  595.         break
  596.  
  597.       elseif item.keys then
  598.  
  599.         Keys(item.BreakKey:gsub("^CS%+","CtrlShift"):gsub("^C%+","Ctrl"))
  600.  
  601.       elseif not item.action then
  602.  
  603.         list:gotoWarning(pos)
  604.  
  605.       else
  606.  
  607.         pos = item.action(pos,Items) or pos
  608.  
  609.         if pos=="break" then break end
  610.  
  611.       end
  612.  
  613.     until false
  614.  
  615.     only_globals = false
  616.  
  617.   end
  618.  
  619. end
  620.  
  621.  
  622.  
  623. Event { description="luacheck menu handler";
  624.  
  625.   group="DialogEvent";
  626.  
  627.   action=function(Event,param)
  628.  
  629.     local hDlg,Msg = param.hDlg,param.Msg
  630.  
  631.     if Msg==F.DN_RESIZECONSOLE then
  632.  
  633.       if Event==F.DE_DLGPROCINIT and Menu.Id==Id then
  634.  
  635.         hDlg:send(F.DM_CLOSE,-1,0)
  636.  
  637.         list:calcProps()
  638.  
  639.       end
  640.  
  641.     elseif Msg==F.DN_INITDIALOG and Event==F.DE_DLGPROCINIT then
  642.  
  643.       local info = hDlg:send(F.DM_GETDIALOGINFO)
  644.  
  645.       if info and info.Id==win.Uuid(Id) then
  646.  
  647.         local r = hDlg:send(F.DM_GETITEMPOSITION,1)
  648.  
  649.         hDlg:send(F.DM_SETITEMPOSITION,1,{Left=r.Left-2,Top=r.Top-1,Right=r.Right-2,Bottom=r.Bottom-1})
  650.  
  651.         r = hDlg:send(F.DM_GETDLGRECT)
  652.  
  653.         hDlg:send(F.DM_RESIZEDIALOG,0,{Y=r.Bottom-r.Top-1,X=r.Right-r.Left-3})
  654.  
  655.         hDlg:send(F.DM_MOVEDIALOG,0,{X=2,Y=list.Pos=="Bottom" and 1 or 0})
  656.  
  657.       end
  658.  
  659.     end
  660.  
  661.   end
  662.  
  663. }
  664.  
  665.  
  666.  
  667. Macro { description="luacheck menu helper";
  668.  
  669.   area="Menu";  key="ShiftUp ShiftDown";    flags="NoSendKeysToPlugins";
  670.  
  671.   uid="60596FEB-E7C5-47A5-A3C9-B782C8F8EF93";
  672.  
  673.   condition=function()return O.AutoPos and Menu.Id==Id end;
  674.  
  675.   action=function()
  676.  
  677.     Keys(mf.akey(1,1):match"Up" and "Num8" or "Num2")
  678.  
  679.   end;
  680.  
  681. }
  682.  
  683.  
  684.  
  685. Macro { description="luacheck: process current editor";
  686.  
  687.   area="Editor";    key="CtrlShiftF7";  filemask="*.lua";
  688.  
  689.   uid="CE634ECE-1039-43F3-80CC-8BB17B1FDB05";
  690.  
  691.   action=Check;
  692.  
  693. }</span></span></span>

User avatar
John Doe
Бюрократ
Posts: 11076
Joined: Wed 27 Apr, 2005 20:42
Has thanked: 11 times
Been thanked: 64 times

luacheck — статический анализатор для Lua

Post by John Doe » Tue 21 Jun, 2016 15:10

Ни один из предложенных мной варианта в шапку пока не пойдёт, т.к. не соответствуют моему видению процесса отладки кода.
Ведь (в идеале) требуется избавиться от всех предупреждений.

Замечу, что изменение кода это не единственный путь "избавления".
Luacheck всего лишь предупреждает, и если какой-то приём в коде использован сознательно, то можно просто подавить предупреждение, например с помощью inline-опций (есть и другие варианты, но не суть).

Впрочем, не исключаю, что действительно может есть смысл рассматривать различные группы предупреждений по отдельности.
Т.е. например:
- можно сортировать список не в порядке следования, а по кодам
- или как вы и предлагали фильтровать список, но тогда не только по "1", а и по прочим группам.

User avatar
HaRT
Moderator
Posts: 7984
Joined: Tue 30 Aug, 2005 17:21
Location: Санкт-Петербург
Has thanked: 66 times
Been thanked: 97 times

luacheck — статический анализатор для Lua

Post by HaRT » Tue 21 Jun, 2016 16:22

John Doe wrote: здесь просто скрывается всё что не начинается на "1", но зато список не закрывается
Спасибо, погоняю.
John Doe wrote: рассматривать различные группы предупреждений по отдельности
Мне вот тоже уже приходило в голову, что, возможно, имело бы смысл сопоставить каждому предупреждению тэги (хоть по тем же опциям luacheck), и фильтровать, включая/выключая те или иные тэги. Но я больших программ на Луа не пишу, поэтому не могу утверждать, как будет удобно при серьёзной разработке.
Фар есть инструмент, а не нянька. © 2009 DrKnS

User avatar
John Doe
Бюрократ
Posts: 11076
Joined: Wed 27 Apr, 2005 20:42
Has thanked: 11 times
Been thanked: 64 times

luacheck — статический анализатор для Lua

Post by John Doe » Tue 21 Jun, 2016 21:47

Заметил, что моя рабочая версия отличается от выложенной в шапке.
Изменения больше внутренние, но для порядка обновил.

IgorZ
Posts: 448
Joined: Wed 13 Jul, 2011 03:32
Has thanked: 5 times
Been thanked: 8 times

luacheck — статический анализатор для Lua

Post by IgorZ » Thu 28 Jul, 2016 05:37

Случайно заметил ошибку:

В обоих макросах uid="60596FEB-E7C5-47A5-A3C9-B782C8F8EF93"

User avatar
John Doe
Бюрократ
Posts: 11076
Joined: Wed 27 Apr, 2005 20:42
Has thanked: 11 times
Been thanked: 64 times

luacheck — статический анализатор для Lua

Post by John Doe » Thu 28 Jul, 2016 06:13

Я тоже нашёл её случайно, в процессе перехода на id )
Во втором будет id="CE634ECE-1039-43F3-80CC-8BB17B1FDB05";

Shmuel
Posts: 5041
Joined: Thu 23 Mar, 2006 21:36
Location: Israel
Has thanked: 11 times
Been thanked: 133 times

luacheck — статический анализатор для Lua

Post by Shmuel » Thu 28 Jul, 2016 06:15

Возможно LuaMacro должен это ловить и выдавать сообщения?

User avatar
John Doe
Бюрократ
Posts: 11076
Joined: Wed 27 Apr, 2005 20:42
Has thanked: 11 times
Been thanked: 64 times

luacheck — статический анализатор для Lua

Post by John Doe » Thu 28 Jul, 2016 06:23

Возможно, но позиция изложенная тут мне кажется обоснованной.
Если когда-нибудь в фаре появится окошко с логом, то там таким ошибком самое место.

А сейчас как вариант можно при обнаружении такой ошибки создавать в таблице макроса поле error = "duplicated id", а макробраузеры сделают остальное.

P.S.
В rebind есть возможность отлавливать такие ошибки, но если будет официальное поле error, то пожалуй тоже уберу.

User avatar
HaRT
Moderator
Posts: 7984
Joined: Tue 30 Aug, 2005 17:21
Location: Санкт-Петербург
Has thanked: 66 times
Been thanked: 97 times

luacheck — статический анализатор для Lua

Post by HaRT » Thu 28 Jul, 2016 11:38

John Doe wrote: можно при обнаружении такой ошибки создавать в таблице макроса поле error = "duplicated id", а макробраузеры сделают остальное.
Если уж что-то такое и делать, то я бы предложил что-то более структурное, чем одна строка. Как минимум нужен массив строк, т.к. ошибок в одном макросе может быть несколько. Далее, с каждой ошибкой может ассоциироваться позиция в коде, а то и две или три. Ещё, поскольку с макросами работают разные плагины/макросы, неплохо бы иметь возможность задать в отдельном поле „источник“ ошибки. Ну и так далее — одним словом, есть, что обдумать/обсудить.
Last edited by HaRT on Thu 01 Jan, 1970 01:00, edited 0 times in total.
Reason: Подчёркнуто главное
Фар есть инструмент, а не нянька. © 2009 DrKnS

User avatar
John Doe
Бюрократ
Posts: 11076
Joined: Wed 27 Apr, 2005 20:42
Has thanked: 11 times
Been thanked: 64 times

luacheck — статический анализатор для Lua

Post by John Doe » Thu 28 Jul, 2016 14:57

HaRT
Пока что формально это внутренняя приватная структура плагина, недокументированная и подверженная внезапным изменениям.
Можно долго обдумывать, а потом ничего этого так и не пригодится.

А можно долго не думать, а изменить значение на таблицу тогда, когда возникнет реальная необходимость.

Вместо error можно завести поле duplicated_id

User avatar
HaRT
Moderator
Posts: 7984
Joined: Tue 30 Aug, 2005 17:21
Location: Санкт-Петербург
Has thanked: 66 times
Been thanked: 97 times

luacheck — статический анализатор для Lua

Post by HaRT » Thu 28 Jul, 2016 15:49

John Doe wrote: формально это внутренняя приватная структура плагина, недокументированная и подверженная внезапным изменениям
Это вступает в противоречие с высказанным ранее:
John Doe wrote: макробраузеры сделают остальное
John Doe wrote: Вместо error можно завести поле duplicated_id
Ещё хуже, ибо это отдельное поле, заточенное под конкретную ошибку.
Фар есть инструмент, а не нянька. © 2009 DrKnS

User avatar
John Doe
Бюрократ
Posts: 11076
Joined: Wed 27 Apr, 2005 20:42
Has thanked: 11 times
Been thanked: 64 times

luacheck — статический анализатор для Lua

Post by John Doe » Thu 28 Jul, 2016 15:58

HaRT wrote: Это вступает в противоречие с высказанным ранее:
Не знаю насчёт противоречий, но дела обстоят именно так: структура лишь косвенно документирована, и отдельные её элементы могут меняться (и меняются) без предупреждения.

А макробраузеры приспосабливаются.

User avatar
John Doe
Бюрократ
Posts: 11076
Joined: Wed 27 Apr, 2005 20:42
Has thanked: 11 times
Been thanked: 64 times

luacheck — статический анализатор для Lua

Post by John Doe » Sun 28 Aug, 2016 21:17

1.3.0-beta: Поддержка moonscript
1.3.1-beta: С этим мунскриптом непросто всё
1.3.2-beta: Обработка синтаксических ошибок.

Update
Прогнал на исходном коде moonscript, по результатам кое-что исправил/усовершенствовал.
1.3.3 в шапке.

lysenkov
Posts: 2
Joined: Wed 15 Mar, 2017 18:50
Has thanked: 1 time

luacheck — статический анализатор для Lua

Post by lysenkov » Wed 15 Mar, 2017 18:52

Скажите, куда положить .luacheckrc, чтобы он загрузился?

User avatar
John Doe
Бюрократ
Posts: 11076
Joined: Wed 27 Apr, 2005 20:42
Has thanked: 11 times
Been thanked: 64 times

luacheck — статический анализатор для Lua

Post by John Doe » Sun 19 Mar, 2017 17:20

По замыслу он предполагается в текущей папке, или выше (вплоть до корня). В контексте фара это не очень надёжно, и я даже не проверял работает ли.
На практике конфигурацию можно задать прямо в luacheck_editor.lua, а если не хочется трогать исходник, то использовать возможности cfgscript.

User avatar
HaRT
Moderator
Posts: 7984
Joined: Tue 30 Aug, 2005 17:21
Location: Санкт-Петербург
Has thanked: 66 times
Been thanked: 97 times

luacheck — статический анализатор для Lua

Post by HaRT » Sun 19 Mar, 2017 21:02

John Doe wrote: По замыслу он предполагается в текущей папке, или выше (вплоть до корня). В контексте фара это не очень надёжно, и я даже не проверял работает ли.
Так может лучше от папки проверяемого файла?
Фар есть инструмент, а не нянька. © 2009 DrKnS

Post Reply

Return to “Обсуждение макросов”

Who is online

Users browsing this forum: No registered users and 2 guests