Merge lp:~openerp-community/openobject-client/zehk_use-of-xdg-open into lp:openobject-client

Proposed by Thierry Treyer
Status: Needs review
Proposed branch: lp:~openerp-community/openobject-client/zehk_use-of-xdg-open
Merge into: lp:openobject-client
Diff against target: 177 lines (+30/-116)
1 file modified
bin/printer/printer.py (+30/-116)
To merge this branch: bzr merge lp:~openerp-community/openobject-client/zehk_use-of-xdg-open
Reviewer Review Type Date Requested Status
Naresh(OpenERP) Needs Fixing
Review via email: mp+77333@code.launchpad.net

Description of the change

Add the use of xdg-open, gnome-open and kde-open to the method used to determine which program should be launched to print the data of a Binary fields.

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

On Wednesday 28 September 2011, Zehk' wrote:
> Zehk' has proposed merging
> lp:~openerp-community/openobject-client/zehk_use-of-xdg-open into
> lp:openobject-client.
>
> For more details, see:
> https://code.launchpad.net/~openerp-community/openobject-client/zehk_use-of
> -xdg-open/+merge/77333
>
> Add the use of xdg-open, gnome-open and kde-open to the method used to
> determine which program should be launched to print the data of a Binary
> fields.

Many thanks!
the previous code has been a "shame to have" ..

--
Say NO to spam and viruses. Stop using Microsoft Windows!

Revision history for this message
Naresh(OpenERP) (nch-openerp) wrote :

Hello Zehk,

It seems a good work but I have few doubts... Why do you need to add this extra check for 'posix' and for file types ['xdg-open', 'gnome-open', 'kde-open'] dont we have this check in _findPDFOpener except for the 'kde-open'opener (which can be added there itself) at line 107.

AFAIS the current system do make a check for the applications to be loaded to open the files based on their types or am I missing something ?

Thanks,

review: Needs Information
1961. By Thierry Treyer

Use of _findInPath

Revision history for this message
Thierry Treyer (zehkae) wrote :

> Hello Zehk,
>
> It seems a good work but I have few doubts... Why do you need to add this
> extra check for 'posix' and for file types ['xdg-open', 'gnome-open', 'kde-
> open'] dont we have this check in _findPDFOpener except for the 'kde-
> open'opener (which can be added there itself) at line 107.
>
> AFAIS the current system do make a check for the applications to be loaded to
> open the files based on their types or am I missing something ?
>
>
> Thanks,

Hello,

The problem is when you want to open a document, but don't use OpenOffice (LibreOffice, for instance).
The client is not able to detect LibreOffice, so it won't open your document and will finally crash.
It was tested on Debian 6.0.2, using the packaged version of openerp-client (5.0.12) and using the latest version from the bzr repository.

In addition of using a defined list of application, it add a step to check if it can use 'xdg-open', that will take care of finding which application should be launched, according to the user preferences.

Finally, I've just modified the code to use _findInPath, instead of defining a function that do the same job.

Revision history for this message
Naresh(OpenERP) (nch-openerp) wrote :

Hello,

Is doing this not enough ?

nch@Naresh:~/workspace/OpenERP2011/Trunk/client/bin$ bzr diff
=== modified file 'bin/printer/printer.py'
--- bin/printer/printer.py 2011-03-17 12:59:55 +0000
+++ bin/printer/printer.py 2011-10-04 08:57:06 +0000
@@ -104,7 +104,7 @@
         else:
             if options.options['printer.preview']:
                 if not softpath or (softpath and softpath in ['None','none']):
- prog = self._findInPath(['xdg-open', 'gnome-open', 'see'])
+ prog = self._findInPath(['xdg-open', 'gnome-open', 'see','kde-open'])
                     return self._opener(lambda fn: os.execv(prog, (os.path.basename(prog), fn)))
                 else:
                     return self._opener(lambda fn: os.execv(softpath, (os.path.basename(softpath), fn)))

correct me if I am missing something !

Regards,

review: Needs Fixing
Revision history for this message
Thierry Treyer (zehkae) wrote :

> Hello,
>
> Is doing this not enough ?
>
> nch@Naresh:~/workspace/OpenERP2011/Trunk/client/bin$ bzr diff
> === modified file 'bin/printer/printer.py'
> --- bin/printer/printer.py 2011-03-17 12:59:55 +0000
> +++ bin/printer/printer.py 2011-10-04 08:57:06 +0000
> @@ -104,7 +104,7 @@
> else:
> if options.options['printer.preview']:
> if not softpath or (softpath and softpath in
> ['None','none']):
> - prog = self._findInPath(['xdg-open', 'gnome-open',
> 'see'])
> + prog = self._findInPath(['xdg-open', 'gnome-open', 'see
> ','kde-open'])
> return self._opener(lambda fn: os.execv(prog,
> (os.path.basename(prog), fn)))
> else:
> return self._opener(lambda fn: os.execv(softpath,
> (os.path.basename(softpath), fn)))
>
> correct me if I am missing something !
>
> Regards,

The problem is not with the PDF opener, it is in general.

If he can't find the right application by using your list (defined for instance in line 119), it will search for another one who will open the document according with the user preferences.

Revision history for this message
Thierry Treyer (zehkae) wrote :

xdg-open can open any type of file, not only PDF. That's why we can use it to open any file.

1962. By Thierry Treyer

Rewrite the Printer module

1963. By Thierry Treyer

Fix the Windows part

1964. By Thierry Treyer

Merge from main branche

Revision history for this message
Thierry Treyer (zehkae) wrote :

Hello,

I rewrote the Printer module.
Now, it use a default opener, according to the OS (start on Windows, open on Mac, xdg-open on Linux,…).

It has been tested on Debian 6.0.3, Windows XP and on Mac OS X (with the OpenERP Client 5).

Revision history for this message
Thierry Treyer (zehkae) wrote :

Hello everyone,

I didn't receive any comment since a while, so I come back.
I took into account your remarks and modify the code acordingly.

I would like to have some feedbacks.

Thanks

Revision history for this message
Naresh(OpenERP) (nch-openerp) wrote :

Hello Thierry,

Thanks for your valuable contribution ! Just a few comments ! There's always a big risk associated when you make a big change, risk like loosing essential features, regressions etc. Its should be tested and well executed keeping in mind the previous functionalities offered. By loosing essential features I meant that Currently OpenERP allows you to define your own extensions from the extension manager options from the toolbar(GTK client) options/extension manager for eg: I would like to open/print *XYZ* extension files with firefox. Then OpenERP gives higher priority to the extensions defined by the user if found use them else go for the other openers according to extension type. So with your merge proposal this features gets lost.
secondly: OpenERP allows users to define their softpath(usually for pdf) and softpath_html(usuallyfor html types) i.e
If you want to use another PDF viewer or if you do not want to use the first one the OpenERP will find for you, you have to edit the OpenERP configuration file, normally located in ~/.openerprc and in the [printer] section edit the softpath and softpath_html parameter. This feature is also lost with your merge proposal.
Thirdly: can you please refactor your code please like remove the unused imports, unnecessary dict(self.openers) can be just a list as they all gives the same self._findOpener function.

please before making such changes please have a deep look at the existing system working and the features it provides. For eg: if you remove a line then first just think why was the line introduced. do I cover the intension in my new proposal etc.

Once again thanks for your work and patience ! Hope to see the improved merge soon.

Regards,

review: Needs Fixing
Revision history for this message
Etienne Bagnoud (etienne-bagnoud) wrote :

Hi,

I'm interested in sorting out this bug and have followed this thread. I think the rewrite of the module might be too much, but the original proposition was pretty good as it didn't introduce any regression (not modifying too much code) and worked.
xdg-open is part of XdgUtils which make it simpler for an application to use the correct program to open any given file or URL (http://portland.freedesktop.org/wiki/). OpenERP GTK Client uses xdg-open only for pdf file and an intern list for others application. When it doesn't find the right application it just crash. The first proposition keeps the original solution while adding the correct way of opening a file under operating systems that respect freedesktop and user's preferences.

Of course a rewrite is needed for this module, using a generic file opener (xdg-open) and not for others files shows a lack of understanding of what does xdg-open.

Maybe the first proposition should be merged in stable branch as first easy step : it correct a bug under Debian (and maybe others distributions) and does not introduce any regression and the last proposition should be made a basis for a new correct code for opening a file.

My 2 cents.
Etienne.

Unmerged revisions

1964. By Thierry Treyer

Merge from main branche

1963. By Thierry Treyer

Fix the Windows part

1962. By Thierry Treyer

Rewrite the Printer module

1961. By Thierry Treyer

Use of _findInPath

1960. By Thierry Treyer

Using xdg-open, gnome-open and kde-open to open the file of a Binary field

1959. By Thierry Treyer

Merge from main branch

Preview Diff

[H/L] Next/Prev Comment, [J/K] Next/Prev File, [N/P] Next/Prev Hunk
1=== modified file 'bin/printer/printer.py'
2--- bin/printer/printer.py 2011-03-17 12:59:55 +0000
3+++ bin/printer/printer.py 2011-10-13 08:37:34 +0000
4@@ -44,144 +44,58 @@
5
6 def __init__(self):
7 self.openers = {
8- 'pdf': self._findPDFOpener,
9- 'html': self._findHTMLOpener,
10- 'doc': self._findHTMLOpener,
11- 'xls': self._findHTMLOpener,
12- 'sxw': self._findSXWOpener,
13- 'odt': self._findSXWOpener,
14- 'tiff': self._findPDFOpener,
15+ 'pdf': self._findOpener,
16+ 'html': self._findOpener,
17+ 'doc': self._findOpener,
18+ 'xls': self._findOpener,
19+ 'sxw': self._findOpener,
20+ 'odt': self._findOpener,
21+ 'tiff': self._findOpener,
22 }
23
24 def _findInPath(self, progs):
25 lstprogs = progs[:]
26- found = {}
27- path = [dir for dir in os.environ['PATH'].split(':')
28+ path = [dir for dir in os.environ['PATH'].split(os.pathsep)
29 if os.path.isdir(dir)]
30 for dir in path:
31 content = os.listdir(dir)
32- for prog in progs[:]:
33+ for prog in lstprogs:
34 if prog in content:
35 return os.path.join(dir, prog)#prog
36-
37- progs.remove(prog)
38- found[prog] = os.path.join(dir, prog)
39- for prog in lstprogs:
40- if prog in found:
41- return found[prog]
42 return ''
43
44- def _findHTMLOpener(self):
45- import webbrowser
46- def opener(fn):
47- webbrowser.open('file://'+fn)
48- return opener
49-
50 def _opener(self, fnct):
51 def opener(fn):
52 pid = os.fork()
53 if not pid:
54- pid = os.fork()
55- if not pid:
56- fnct(fn)
57- time.sleep(0.1)
58- sys.exit(0)
59+ fnct(fn)
60 os.waitpid(pid, 0)
61 return opener
62+
63+ def _findOpener(self):
64+ app_to_run, opener = None, None
65
66- def _findPDFOpener(self):
67- if platform.system() == 'Darwin':
68- return self._opener(lambda fn: os.system('open ' + fn))
69- softpath = options.options['printer.softpath']
70 if platform.system() == 'Windows':
71- if options.options['printer.preview']:
72- if not softpath or (softpath and softpath in ['None','none']):
73- return os.startfile
74- else:
75- return lambda fn: os.system(softpath + ' ' + fn)
76- else:
77- return print_w32_filename
78- else:
79- if options.options['printer.preview']:
80- if not softpath or (softpath and softpath in ['None','none']):
81- prog = self._findInPath(['xdg-open', 'gnome-open', 'see'])
82- return self._opener(lambda fn: os.execv(prog, (os.path.basename(prog), fn)))
83- else:
84- return self._opener(lambda fn: os.execv(softpath, (os.path.basename(softpath), fn)))
85- else:
86- return print_linux_filename
87-
88- def _findSXWOpener(self):
89- if os.name == 'nt':
90- return lambda fn: os.startfile(fn)
91- else:
92- if options.options['printer.softpath_html'] is None:
93- prog = self._findInPath(['ooffice', 'ooffice2', 'openoffice', 'soffice'])
94- def opener(fn):
95- pid = os.fork()
96- if not pid:
97- pid = os.fork()
98- if not pid:
99- os.execv(prog, (os.path.basename(prog),fn))
100- time.sleep(0.1)
101- sys.exit(0)
102- os.waitpid(pid, 0)
103- return opener
104- else:
105- def opener(fn):
106- pid = os.fork()
107- if not pid:
108- pid = os.fork()
109- if not pid:
110- os.execv(options.options['printer.softpath_html'], (os.path.basename(options.options['printer.softpath_html']),fn))
111- time.sleep(0.1)
112- sys.exit(0)
113- os.waitpid(pid, 0)
114- return opener
115+ opener = os.startfile
116+ elif platform.system() == 'Darwin':
117+ app_to_run = self._findInPath(['open'])
118+ else:
119+ app_to_run = self._findInPath(['xdg-open', 'gnome-open', 'kde-open'])
120+
121+ if app_to_run:
122+ opener = self._opener(lambda fn: os.execv(app_to_run, (os.path.basename(app_to_run), fn)))
123+
124+ return opener
125+
126 def print_file(self, fname, ftype, preview=False):
127- app_to_run = None
128- try:
129- filetypes = eval( options.options['extensions.filetype'] )
130- (app, app_print) = filetypes[ftype]
131- if options.options['printer.preview'] or preview:
132- app_to_run = app
133- else:
134- app_to_run = app_print
135- except:
136- pass
137-
138- if app_to_run:
139- def open_file(cmd, filename):
140- cmd = cmd.split()
141- found = False
142- for i, v in enumerate(cmd):
143- if v == '%s':
144- cmd[i] = filename
145- found = True
146- break
147- if not found:
148- cmd.append(filename)
149-
150- import subprocess
151- subprocess.Popen(cmd)
152- open_file(app_to_run, fname)
153-
154- else:
155+ opener = self._findOpener()
156+ if opener:
157 try:
158- finderfunc = self.openers.get(ftype,False)
159- if not finderfunc:
160- if sys.platform in ['win32', 'nt']:
161- os.startfile(fname)
162- else:
163- finderfunc = self.openers['html']
164- opener = finderfunc()
165- opener(fname)
166- else:
167- opener = finderfunc()
168- opener(fname)
169- gc.collect()
170- except Exception,e:
171+ opener(fname)
172+ except:
173 raise Exception(_('Unable to handle %s filetype') % ftype)
174+ else:
175+ raise Exception(_('Unable to handle %s filetype') % ftype)
176
177 printer = Printer()
178