libs/core: luci.model.ipkg: Use OPKG instead of IPKG if available
[project/luci.git] / libs / core / luasrc / model / ipkg.lua
1 --[[
2 LuCI - IPKG wrapper library
3
4 Description:
5 Wrapper for the ipkg Package manager
6
7 Any return value of false or nil can be interpreted as an error
8
9 FileId:
10 $Id$
11
12 License:
13 Copyright 2008 Steven Barth <steven@midlink.org>
14
15 Licensed under the Apache License, Version 2.0 (the "License");
16 you may not use this file except in compliance with the License.
17 You may obtain a copy of the License at 
18
19         http://www.apache.org/licenses/LICENSE-2.0 
20
21 Unless required by applicable law or agreed to in writing, software
22 distributed under the License is distributed on an "AS IS" BASIS,
23 WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
24 See the License for the specific language governing permissions and
25 limitations under the License.
26
27 ]]--
28 module("luci.model.ipkg", package.seeall)
29 require("luci.sys")
30 require("luci.util")
31 require("luci.fs")
32
33 ipkg = luci.fs.access("/bin/opkg") and "opkg" or "ipkg"
34
35 -- Returns repository information
36 function info(pkg)
37         return _lookup("info", pkg)
38 end
39
40 -- Returns a table with status information
41 function status(pkg)
42         return _lookup("status", pkg)
43 end
44
45 -- Installs packages
46 function install(...)
47         return _action("install", ...)
48 end
49
50 -- Returns whether a package is installed
51 function installed(pkg, ...)
52         local p = status(...)[pkg]
53         return (p and p.Status and p.Status.installed)
54 end
55
56 -- Removes packages
57 function remove(...)
58         return _action("remove", ...)
59 end
60
61 -- Updates package lists
62 function update()
63         return _action("update")
64 end
65
66 -- Upgrades installed packages
67 function upgrade()
68         return _action("upgrade")
69 end
70
71
72 -- Internal action function
73 function _action(cmd, ...)
74         local pkg = ""
75         arg.n = nil
76         for k, v in pairs(arg) do
77                 pkg = pkg .. " '" .. v:gsub("'", "") .. "'"
78         end
79         
80         local c = ipkg.." "..cmd.." "..pkg.." >/dev/null 2>&1"
81         local r = os.execute(c)
82         return (r == 0), r      
83 end
84
85 -- Internal lookup function
86 function _lookup(act, pkg)
87         local cmd = ipkg .. " " .. act
88         if pkg then
89                 cmd = cmd .. " '" .. pkg:gsub("'", "") .. "'"
90         end
91         
92         return _parselist(luci.sys.exec(cmd .. " 2>/dev/null"))
93 end
94
95 -- Internal parser function
96 function _parselist(rawdata)    
97         if type(rawdata) ~= "string" then
98                 error("IPKG: Invalid rawdata given")
99         end
100         
101         rawdata = luci.util.split(rawdata) 
102         local data = {}
103         local c = {}
104         local l = nil
105         
106         for k, line in pairs(rawdata) do
107                 if line:sub(1, 1) ~= " " then
108                         local split = luci.util.split(line, ":", 1)
109                         local key = nil
110                         local val = nil
111                         
112                         if split[1] then
113                                 key = luci.util.trim(split[1])
114                         end
115                         
116                         if split[2] then
117                                 val = luci.util.trim(split[2])
118                         end
119                         
120                         if key and val then
121                                 if key == "Package" then
122                                         c = {Package = val}
123                                         data[val] = c
124                                 elseif key == "Status" then
125                                         c.Status = {}
126                                         for i, j in pairs(luci.util.split(val, " ")) do
127                                                 c.Status[j] = true
128                                         end
129                                 else
130                                         c[key] = val
131                                 end
132                                 l = key
133                         end
134                 else
135                         -- Multi-line field
136                         c[l] = c[l] .. "\n" .. line:sub(2)
137                 end
138         end
139         
140         return data
141 end