Merge lp:~frederik-elwert/lens-cooking/chefkoch-scope into lp:lens-cooking

Proposed by Frederik Elwert
Status: Merged
Approved by: Eduard Gotwig
Approved revision: 44
Merge reported by: Eduard Gotwig
Merged at revision: not available
Proposed branch: lp:~frederik-elwert/lens-cooking/chefkoch-scope
Merge into: lp:lens-cooking
Diff against target: 331 lines (+233/-13)
8 files modified
chefkoch.scope (+3/-0)
chefkoch.svg (+71/-0)
debian/unity-lens-cooking.install (+7/-4)
setup.py (+9/-2)
unity-lens-cooking (+7/-5)
unity-scope-chefkoch (+131/-0)
unity-scope-chefkoch.service (+3/-0)
unity-scope-gourmet (+2/-2)
To merge this branch: bzr merge lp:~frederik-elwert/lens-cooking/chefkoch-scope
Reviewer Review Type Date Requested Status
Eduard Gotwig Approve
Review via email: mp+106897@code.launchpad.net

Description of the change

Added scope for chefkoch.de and added this as a new category to the lens.

To post a comment you must log in.
Revision history for this message
Eduard Gotwig (gotwig) wrote :

Approved, thank you for your big help :-)!

review: Approve
Revision history for this message
Eduard Gotwig (gotwig) wrote :

I am going to merge this in 5 hours.

Preview Diff

[H/L] Next/Prev Comment, [J/K] Next/Prev File, [N/P] Next/Prev Hunk
=== added file 'chefkoch.scope'
--- chefkoch.scope 1970-01-01 00:00:00 +0000
+++ chefkoch.scope 2012-05-22 20:35:21 +0000
@@ -0,0 +1,3 @@
1[Scope]
2DBusName=net.launchpad.scope.cooking.chefkoch
3DBusPath=/net/launchpad/scope/cooking/chefkoch
04
=== added file 'chefkoch.svg'
--- chefkoch.svg 1970-01-01 00:00:00 +0000
+++ chefkoch.svg 2012-05-22 20:35:21 +0000
@@ -0,0 +1,71 @@
1<?xml version="1.0" encoding="UTF-8" standalone="no"?>
2<!-- Created with Inkscape (http://www.inkscape.org/) -->
3
4<svg
5 xmlns:dc="http://purl.org/dc/elements/1.1/"
6 xmlns:cc="http://creativecommons.org/ns#"
7 xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#"
8 xmlns:svg="http://www.w3.org/2000/svg"
9 xmlns="http://www.w3.org/2000/svg"
10 xmlns:sodipodi="http://sodipodi.sourceforge.net/DTD/sodipodi-0.dtd"
11 xmlns:inkscape="http://www.inkscape.org/namespaces/inkscape"
12 width="32.625004"
13 height="28.500004"
14 id="svg3018"
15 version="1.1"
16 inkscape:version="0.48.3.1 r9886"
17 sodipodi:docname="chefkoch.svg">
18 <defs
19 id="defs3020" />
20 <sodipodi:namedview
21 id="base"
22 pagecolor="#ffffff"
23 bordercolor="#666666"
24 borderopacity="1.0"
25 inkscape:pageopacity="0.0"
26 inkscape:pageshadow="2"
27 inkscape:zoom="2.8"
28 inkscape:cx="0.096507634"
29 inkscape:cy="4.5050419"
30 inkscape:document-units="px"
31 inkscape:current-layer="layer1"
32 showgrid="false"
33 fit-margin-top="0"
34 fit-margin-left="0"
35 fit-margin-right="0"
36 fit-margin-bottom="0"
37 inkscape:window-width="1301"
38 inkscape:window-height="744"
39 inkscape:window-x="65"
40 inkscape:window-y="24"
41 inkscape:window-maximized="1" />
42 <metadata
43 id="metadata3023">
44 <rdf:RDF>
45 <cc:Work
46 rdf:about="">
47 <dc:format>image/svg+xml</dc:format>
48 <dc:type
49 rdf:resource="http://purl.org/dc/dcmitype/StillImage" />
50 <dc:title></dc:title>
51 </cc:Work>
52 </rdf:RDF>
53 </metadata>
54 <g
55 inkscape:label="Ebene 1"
56 inkscape:groupmode="layer"
57 id="layer1"
58 transform="translate(-335.3125,-518.46875)">
59 <path
60 inkscape:connector-curvature="0"
61 id="path3219"
62 d="m 342.15481,519.26909 c -3.31663,-0.003 -6.00944,2.58203 -6.01217,5.77118 -0.002,2.7707 2.02629,5.09149 4.7339,5.65418 l -0.0132,15.43625 21.50651,0.0183 0.0132,-15.43622 c 2.70857,-0.55807 4.74117,-2.8754 4.74353,-5.64609 0.003,-3.18916 -2.68563,-5.77862 -6.00229,-5.78146 -1.9333,-0.002 -3.65477,0.87481 -4.75521,2.23917 -1.09836,-1.36232 -2.80673,-2.24563 -4.73683,-2.24728 -1.92681,-0.002 -3.63969,0.86865 -4.74061,2.22516 -1.09859,-1.35838 -2.80999,-2.23161 -4.73683,-2.23325 z"
63 style="fill:#eef4f3;fill-opacity:1;fill-rule:evenodd;stroke:#4c6f0f;stroke-width:1.62983214999999992;stroke-linecap:round;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none;stroke-dashoffset:0" />
64 <path
65 style="fill:none;fill-opacity:1;fill-rule:evenodd;stroke:#4c6f0f;stroke-width:1.62999999999999967;stroke-linecap:butt;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none;stroke-dashoffset:0"
66 d="m 340.73707,540.8274 21.38024,0.0183"
67 id="path4436"
68 inkscape:connector-curvature="0"
69 sodipodi:nodetypes="cc" />
70 </g>
71</svg>
072
=== modified file 'debian/unity-lens-cooking.install'
--- debian/unity-lens-cooking.install 2012-04-06 14:37:30 +0000
+++ debian/unity-lens-cooking.install 2012-05-22 20:35:21 +0000
@@ -1,15 +1,18 @@
1build/share/unity/lenses/cooking/cooking.lens /usr/share/unity/lenses/cooking1build/share/unity/lenses/cooking/cooking.lens /usr/share/unity/lenses/cooking
2cooking.svg /usr/share/unity/lenses/cooking2cooking.svg /usr/share/unity/lenses/cooking
3recipefy.png /usr/share/unity/lenses/cooking/icons3recipefy.png /usr/share/unity/lenses/cooking/icons
4chefkoch.svg /usr/share/unity/lenses/cooking/icons
4gourmet.png /usr/share/unity/lenses/cooking/icons5gourmet.png /usr/share/unity/lenses/cooking/icons
5cuisine.png /usr/share/unity/lenses/cooking/icons6cuisine.png /usr/share/unity/lenses/cooking/icons
7unity-lens-cooking /usr/share/unity/lenses/cooking
8unity-lens-cooking.service /usr/share/dbus-1/services
6recipefy.scope /usr/share/unity/lenses/cooking9recipefy.scope /usr/share/unity/lenses/cooking
7unity-lens-cooking /usr/share/unity/lenses/cooking
8unity-scope-recipefy /usr/share/unity/lenses/cooking10unity-scope-recipefy /usr/share/unity/lenses/cooking
9unity-lens-cooking.service /usr/share/dbus-1/services
10unity-scope-recipefy.service /usr/share/dbus-1/services11unity-scope-recipefy.service /usr/share/dbus-1/services
12chefkoch.scope /usr/share/unity/lenses/cooking
13unity-scope-chefkoch /usr/share/unity/lenses/cooking
14unity-scope-chefkoch.service /usr/share/dbus-1/services
15gourmet.scope /usr/share/unity/lenses/cooking
11unity-scope-gourmet /usr/share/unity/lenses/cooking16unity-scope-gourmet /usr/share/unity/lenses/cooking
12unity-scope-gourmet.service /usr/share/dbus-1/services17unity-scope-gourmet.service /usr/share/dbus-1/services
13gourmet.scope /usr/share/unity/lenses/cooking
14build/mo/* /usr/share/locale18build/mo/* /usr/share/locale
15
1619
=== modified file 'setup.py'
--- setup.py 2012-04-04 20:42:32 +0000
+++ setup.py 2012-05-22 20:35:21 +0000
@@ -14,10 +14,17 @@
14 ['unity-lens-cooking',14 ['unity-lens-cooking',
15 'unity-scope-gourmet',15 'unity-scope-gourmet',
16 'unity-scope-recipefy',16 'unity-scope-recipefy',
17 'cooking.svg',]),17 'unity-scope-chefkoch',
18 'chefkoch.svg',
19 'cooking.svg',
20 'cuisine.png',
21 'gourmet.png',
22 ]),
18 ('share/dbus-1/services',23 ('share/dbus-1/services',
19 ['unity-lens-cooking.service',24 ['unity-lens-cooking.service',
20 'unity-scope-gourmet.service',25 'unity-scope-gourmet.service',
21 'unity-scope-recipefy.service',]),26 'unity-scope-recipefy.service',
27 'unity-scope-chefkoch.service',
28 ]),
22 ], cmdclass={"build": build_extra.build_extra,29 ], cmdclass={"build": build_extra.build_extra,
23 "build_i18n": build_i18n.build_i18n,})30 "build_i18n": build_i18n.build_i18n,})
2431
=== modified file 'unity-lens-cooking'
--- unity-lens-cooking 2012-04-05 14:39:09 +0000
+++ unity-lens-cooking 2012-05-22 20:35:21 +0000
@@ -1,6 +1,6 @@
1#! /usr/bin/python1#! /usr/bin/python
2# -*- coding: utf-8 -*-2# -*- coding: utf-8 -*-
3# Copyright 2012 Eduard Gotwig3# Copyright 2012 Eduard Gotwig, Frederik Elwert <frederik.elwert@web.de>
4# License: GPLv34# License: GPLv3
55
6from gi.repository import GLib, GObject, Gio6from gi.repository import GLib, GObject, Gio
@@ -23,8 +23,9 @@
23# Translatable strings23# Translatable strings
2424
2525
26ONLINE = _("Recipefy Recipes")26RECIPEFY = _("Recipefy Recipes")
27LOCAL = _("Gourmet Recipes")27CHEFKOCH = _("Chefkoch Recipes")
28GOURMET = _("Gourmet Recipes")
2829
29LIKES = _("Likes")30LIKES = _("Likes")
30TIME = _("Time")31TIME = _("Time")
@@ -60,8 +61,9 @@
60 ### Then, we populate the categories61 ### Then, we populate the categories
61 cats = []62 cats = []
62 # A category is a display name, an icon and a renderer63 # A category is a display name, an icon and a renderer
63 cats.append (Unity.Category.new (ONLINE,Gio.ThemedIcon.new("/usr/share/unity/lenses/cooking/icons/recipefy.png"),Unity.CategoryRenderer.HORIZONTAL_TILE))64 cats.append (Unity.Category.new (RECIPEFY,Gio.ThemedIcon.new("/usr/share/unity/lenses/cooking/icons/recipefy.png"),Unity.CategoryRenderer.HORIZONTAL_TILE))
64 cats.append (Unity.Category.new (LOCAL,Gio.ThemedIcon.new("/usr/share/unity/lenses/cooking/icons/gourmet.png"),Unity.CategoryRenderer.HORIZONTAL_TILE))65 cats.append (Unity.Category.new (CHEFKOCH,Gio.ThemedIcon.new("/usr/share/unity/lenses/cooking/icons/chefkoch.svg"),Unity.CategoryRenderer.HORIZONTAL_TILE))
66 cats.append (Unity.Category.new (GOURMET,Gio.ThemedIcon.new("/usr/share/unity/lenses/cooking/icons/gourmet.png"),Unity.CategoryRenderer.HORIZONTAL_TILE))
65 self._lens.props.categories = cats67 self._lens.props.categories = cats
66 ### Populate filters NOT IN USE FOR NOW68 ### Populate filters NOT IN USE FOR NOW
67 """filters = []69 """filters = []
6870
=== added file 'unity-scope-chefkoch'
--- unity-scope-chefkoch 1970-01-01 00:00:00 +0000
+++ unity-scope-chefkoch 2012-05-22 20:35:21 +0000
@@ -0,0 +1,131 @@
1#! /usr/bin/python
2# -*- coding: utf-8 -*-
3# Copyright 2012 Eduard Gotwig, Frederik Elwert <frederik.elwert@web.de>
4# License: GPLv3
5
6from gi.repository import GLib, GObject, Gio
7from gi.repository import Dee
8from gi.repository import Unity
9import lxml.html
10import os
11import re
12import gettext
13import locale
14import sys
15
16APP_NAME="unity-lens-cooking"
17LOCAL_PATH="/usr/share/locale"
18
19gettext.bindtextdomain(APP_NAME, LOCAL_PATH)
20gettext.textdomain(APP_NAME)
21_ = gettext.gettext
22
23RUNNING = _("Failed to own name %s. Bailing out. An other instance is already running!")
24
25FULLSTAR_RE = re.compile(r'suche-scrore-(\d).gif')
26HALFSTAR_RE = re.compile(r'suche-scrore-(\d)_(\d).gif')
27
28# The scope dbus id
29BUS_NAME = "net.launchpad.scope.cooking.chefkoch"
30
31class Daemon:
32 def __init__ (self):
33 # Create the scope (this matches the path defined in the .scope file)
34 self.scope = Unity.Scope.new ("/net/launchpad/scope/cooking/chefkoch")
35 # Is the scope searchable from the home dash?
36 self.scope.search_in_global = False
37 # Connect to the search changed signal (it is fired when the lens is opened for the first time, then for each search change)
38 self.scope.connect ("search-changed", self.on_search_changed)
39 # Listen to the lens filters
40 self.scope.connect ("filters-changed", lambda scope : scope.queue_search_changed(Unity.SearchType.DEFAULT))
41 # The scope is ready
42 self.scope.export()
43 # On each search change, this method is called
44 def on_search_changed (self, scope, search, search_type, cancellable):
45 # Get the search string
46 search_string = search.props.search_string.strip()
47 print "Search changed to \"%s\"" % search_string
48 # Get the Dee model (the database used by the lens to store and display search results)
49 model = search.props.results_model
50 # Empty the model
51 model.clear()
52 # Update the model
53 self.update_results_model (search_string, model)
54 # Signal to the lens that the search is finished (the spinning search icon stops)
55 search.finished()
56
57 # Update the model
58 def update_results_model(self, search, model):
59 self.chefkoch(search, model)
60
61 # This method sends the search string to chefkoch and brings back results
62 def chefkoch_search(self,search):
63 # Search for recipes over GET
64 url = ("http://www.chefkoch.de/rs/s0/%s/Rezepte.html" % (search))
65 print "Searching for Recipes at %s" % url
66 tree = lxml.html.parse(url)
67 tree.getroot().make_links_absolute()
68 items = tree.xpath("//table[@class='result']//tr[@bgcolor]")
69 print 'Got %d results' % len(items)
70 return items
71 # This method parses the results and adds them to the model
72 def chefkoch(self, search, model):
73 # Skip empty search
74 if not search:
75 print 'Empty search, skipping.'
76 return
77 # We iterate through each of the returned results
78 for i, item in enumerate(self.chefkoch_search(search)):
79 title = item.xpath("string(td[2]/a)")
80 icon = item.xpath("td[1]/img/@src")[0]
81 if icon == 'http://cdn.chefkoch.de/img/no-image-rsmain.gif':
82 icon = '/usr/share/unity/lenses/cooking/icons/cuisine.png'
83 uri = item.xpath("td[2]/a/@href")[0]
84 stars = {0: '☆☆☆☆☆', 1: '✮☆☆☆☆', 2: '★☆☆☆☆', 3: '★✮☆☆☆', 4: '★★☆☆☆', 5: '★★✮☆☆', 6: '★★★☆☆', 7: '★★★✮☆', 8: '★★★★☆', 9: '★★★★✮', 10: '★★★★★'}
85 likes = 0
86 stars_img = item.xpath("td[3]/img/@src")[0]
87 result = FULLSTAR_RE.search(stars_img)
88 if result:
89 likes = int(result.group(1)) * 2
90 else:
91 result = HALFSTAR_RE.search(stars_img)
92 if result:
93 likes = int(result.group(1)) * 2 + 1
94 time = item[3].text
95 difficulty = item[3].find('br').tail
96 comments = [stars[likes], time + ' ⌚ ', difficulty]
97 comment = ' | '.join(comments)
98
99 # If the uri seems valid, we add the results to the Dee model
100 if (uri.startswith("http://")):
101 # uri, icon, category (matching the order of the categories in the lens), mimetype, title, comment, drag and drop uri
102 model.append(uri, icon, 1, "text/html", title, comment, uri)
103 # We can append the same result to multiple models, just by changing the category
104
105if __name__ == "__main__":
106 # Check if we are running in a German locale. Otherwise, the results are
107 # rather useless, so don't create the daemon.
108 lang = locale.getdefaultlocale()[0]
109 if '_' in lang:
110 lang = lang.split('_', 1)[0]
111 if not lang == 'de':
112 raise SystemExit('No German locale, exiting chefkoch scope')
113 # The following lines take care of the Bus connexion.
114 session_bus_connection = Gio.bus_get_sync (Gio.BusType.SESSION, None)
115 session_bus = Gio.DBusProxy.new_sync (session_bus_connection, 0, None,
116 'org.freedesktop.DBus',
117 '/org/freedesktop/DBus',
118 'org.freedesktop.DBus', None)
119 result = session_bus.call_sync('RequestName',
120 GLib.Variant ("(su)", (BUS_NAME, 0x4)),
121 0, -1, None)
122
123 # Unpack variant response with signature "(u)". 1 means we got it.
124 result = result.unpack()[0]
125
126 if result != 1 :
127 print >> sys.stderr, RUNNING % BUS_NAME
128 raise SystemExit (1)
129
130 daemon = Daemon()
131 GObject.MainLoop().run()
0132
=== added file 'unity-scope-chefkoch.service'
--- unity-scope-chefkoch.service 1970-01-01 00:00:00 +0000
+++ unity-scope-chefkoch.service 2012-05-22 20:35:21 +0000
@@ -0,0 +1,3 @@
1[D-BUS Service]
2Name=net.launchpad.scope.cooking.chefkoch
3Exec=/usr/share/unity/lenses/cooking/unity-scope-chefkoch
04
=== modified file 'unity-scope-gourmet'
--- unity-scope-gourmet 2012-04-07 23:41:13 +0000
+++ unity-scope-gourmet 2012-05-22 20:35:21 +0000
@@ -128,10 +128,10 @@
128 # uri, icon, category (matching the order of the categories in the lens), mimetype, title, comment, drag and drop uri128 # uri, icon, category (matching the order of the categories in the lens), mimetype, title, comment, drag and drop uri
129 if row[14]:129 if row[14]:
130 open('/tmp/unity-scope-gourmet/icon' + str(i), 'wb').write(row[14])130 open('/tmp/unity-scope-gourmet/icon' + str(i), 'wb').write(row[14])
131 model.append(uri, '/tmp/unity-scope-gourmet/icon' + str(i), 1, "text/html", title, comment, uri)131 model.append(uri, '/tmp/unity-scope-gourmet/icon' + str(i), 2, "text/html", title, comment, uri)
132 else:132 else:
133 if os.path.exists('/tmp/unity-scope-gourmet/icon' + str(i)): os.remove('/tmp/unity-scope-gourmet/icon' + str(i))133 if os.path.exists('/tmp/unity-scope-gourmet/icon' + str(i)): os.remove('/tmp/unity-scope-gourmet/icon' + str(i))
134 model.append(uri, '/usr/share/unity/lenses/cooking/icons/cuisine.png', 1, "text/html", title, comment, uri)134 model.append(uri, '/usr/share/unity/lenses/cooking/icons/cuisine.png', 2, "text/html", title, comment, uri)
135 # We can append the same result to multiple models, just by changing the category135 # We can append the same result to multiple models, just by changing the category
136 136
137# The following lines take care of the Bus connexion.137# The following lines take care of the Bus connexion.

Subscribers

People subscribed via source and target branches

to all changes: