From 1a8e242bb3642cf7cb575231533f1ad80d7da9ec Mon Sep 17 00:00:00 2001 From: Valentin Chemiere Date: Wed, 18 Feb 2015 15:45:36 +0100 Subject: [PATCH] Module name --- external_file_location/.__openerp__.py.swp | Bin 0 -> 12288 bytes external_file_location/.attachment.py.swp | Bin 0 -> 12288 bytes external_file_location/.backend.py.swp | Bin 0 -> 12288 bytes external_file_location/__init__.py | 26 +++++++ external_file_location/__openerp__.py | 46 ++++++++++++ external_file_location/attachment.py | 37 ++++++++++ external_file_location/attachment_view.xml | 18 +++++ external_file_location/backend.py | 34 +++++++++ .../backends/.filestore.py.swp | Bin 0 -> 12288 bytes external_file_location/backends/filestore.py | 66 ++++++++++++++++++ external_file_location/backends/ftp.py | 58 +++++++++++++++ external_file_location/backends/sftp.py | 59 ++++++++++++++++ external_file_location/location.py | 39 +++++++++++ external_file_location/location_view.xml | 52 ++++++++++++++ external_file_location/task.py | 48 +++++++++++++ external_file_location/task_view.xml | 47 +++++++++++++ 16 files changed, 530 insertions(+) create mode 100644 external_file_location/.__openerp__.py.swp create mode 100644 external_file_location/.attachment.py.swp create mode 100644 external_file_location/.backend.py.swp create mode 100644 external_file_location/__init__.py create mode 100644 external_file_location/__openerp__.py create mode 100644 external_file_location/attachment.py create mode 100644 external_file_location/attachment_view.xml create mode 100755 external_file_location/backend.py create mode 100644 external_file_location/backends/.filestore.py.swp create mode 100755 external_file_location/backends/filestore.py create mode 100755 external_file_location/backends/ftp.py create mode 100755 external_file_location/backends/sftp.py create mode 100644 external_file_location/location.py create mode 100644 external_file_location/location_view.xml create mode 100644 external_file_location/task.py create mode 100644 external_file_location/task_view.xml diff --git a/external_file_location/.__openerp__.py.swp b/external_file_location/.__openerp__.py.swp new file mode 100644 index 0000000000000000000000000000000000000000..8d9e9bd5ea09629b38a3a52be894b2fc59ae923d GIT binary patch literal 12288 zcmeI2TW=dh6vrn#AZRI|_6r=62Pep0=TZs^Rn={9QcJlQUx+M(tg&}&k67=lW@hbJ zT>1%kMZELG6CZ#}h58u~5}yDGA;dcZ{yW|f3!#*UzEI6b|7?8D%-M5(bH-AX>2JPM zKcd%zn+)US{KsN^|14uuIa2!EaLLontDL3gk~z8SV>hv?BBiQR5)>OH*d@!Df z#P;MQ)oLoLy`D-%B6Qm81?l`TfxX)k@B}U=klA77jcaUYduubFxVHKV-MHSle2w>d z0-k^;;0bsFo`5Id33vjYz*9xQrYr0LDte}3Gj%qpPy&!t1Czz|NlS#`~Rnx82b$R6nX%?1zmxjgC4%f*oV+- z&hEz=?|m|??P1uoUjF|~A%-*1%zI#N*<3*#c85Ro7%+~Gmv zu(IQ{w~HsBk&+RA{q+QrZkQgDn_8C?$O20!iIl zDs>_(cNLa#HSoy}w#L?goX08|(M;Mg*|9W)YrZ4RCjn7?NQts#GD6Vpv9;-LwVIbX zO0q!dQMF)Vs&@hxsjD(FW0l1bjrmlN76T!tA|g%$mCi{G@diN$#~liXL!lKp(mbX{ z)<-ZpTtF@od+aQOH9F14NvnopTPPCQxkCDxrPF%*{z<1z;c=Hv!)6l!yKg#73SKc4i7N)z zqGO2?XIyKZ*t|#=qP>KYKsA!aYKg#@D;G=0xJZo{+>*2i9LLlblo>J1;&OqY08-9t zSjWV<$}}n0xf{fjImKvOO+`N~%1?8aW{mgr=Pt#4jnZ0bXpy6!eU&9>D70Uh1UCI* zIqeiX}w pmsf5SjpWY1>#`GkkJOrtJewywkYnZ53eHC)lhH1@%fPvX{RLiC&r1LR literal 0 HcmV?d00001 diff --git a/external_file_location/.attachment.py.swp b/external_file_location/.attachment.py.swp new file mode 100644 index 0000000000000000000000000000000000000000..dc65a5c0260fc54d033d6e50ac8148dff6dbdf8c GIT binary patch literal 12288 zcmeI2O^+Kj7{^^Mw1pPb-Z(wo1tme*NnZgi-Kyz!w~f?&QIc)7AQU+nPsZwGJlLMi zMxge{6*wR`apqJwa6lYD;xlmN!T}C^1O)s&nd}QHT9A6Fu%-XbiyuGs^LuP3(Yk;B zZflKR4=yv57a5B>KX)Izw9c;Ken$?KcJGfUh26q#W{$9XP#88;s8nM|6_<=_YZ_Ab zxV3x`k3?#FBVl>SE&r$2`=&uQIigEn?Fo1SjzDgsg*Q&IOBXMkcaQUP=jiO2EqCjS zC*TQq0-k^;;0bsFo`5Id3H(n8*z6d4h*+N~<1Kz1;Qm+=p=L;`tCGi z??YFhW6+nI!r1cSF5pE*D@j_k|+?nR_K%`y_lPrcp6S$%k<#ub4!mg zUflELd=}0Qw^}0SGm-sZ6ke$o2JXm!bsdCd@YxM&)5l3o5SGPL7J5)RKh3d_j+i7c@9yOw8 zEVqJ|kYAC6Cg_Mn46IaX_3feyGf4+M#B#voCZ4Pui4ySPEblp5j=3%^{+_zBtHQ!q zr9~Nk33jP+2(e=b0@RafEVQ&3Yeni{{~T+D4H9k)HTMp|u9atCt0NVP!~|>Zf-Es6 zN14)l(||=5!dKx8g-L#0`{bPk!#>ZY#iCAT^u`B+Z)di`Vzn`iR~o+k&E zr8Jn$YN+`rAZkUFDqF`Q5p*@SHd|~o#^Z4?O!GkLVIz?Pks4td*Mh>+w#v!GDo;Wz zh8?$*2h#=4u`^^7Qc?`pGm3;(bj#u432o+mIHNmLhvmSIw4+FA8X?IPA}bQv zD2B1N(q6vZT<!Aaxf*6^0X)YfLIPlWN%YCX`^o zXxb6l;MFwz%&{~v`sq)KA+BnK)=`ng7zM4WJjJ4ed7T9I;{E1ysmxFj0LBDE)VjSI zos7)C&L45}SO$?Bh$#oM=z^gEPccpQ;W!l7%^O8xLm5p<5Z8HbW4!GA@I{{+D?$Ip zN^^^@8c{w6eZlkV{60Qb911M>YsDazG4r$>#+ItfHM)5I!ewffMpQj8sSmcSl@m#Y kIX>0gEZe|BUTJT-(LC9LF)qBifc4>a5!Yi=x0Q@=cS;n4S z_(r4y-e z;!okWNS;WQ){F6+`KXx;kb%;`z;$ZZm)Modmo|N*vbM_4pSwqT$N(8217v^sN1Uujr7=wr40oVYG;567R*Yw`6iwYSa17v^1JX&4U?ys*v4(IeI!Pg-LqlLZ=Cjv9My`X42^PW0|-r|EH8)Ih)cOt@2~6EXlQ< zI6JzRL@R|2gdNR}@+Vp^8#AqV12;g)-)9$^MV{+XoZ_|e#7N;L-3|x$4=S{A$mXj9 z4Wrb@N0ZBi`@zE`11k;UzS`fvr>#%qtI*)DV;pBHb8%cAkZ-Goq3}6M@qt;xJ*@J> z>uhX`+=d&PTdDy+OLnW%4#&QCTeFY Nl4{6{vFmBYegW2uPb2^U literal 0 HcmV?d00001 diff --git a/external_file_location/__init__.py b/external_file_location/__init__.py new file mode 100644 index 00000000..046125d4 --- /dev/null +++ b/external_file_location/__init__.py @@ -0,0 +1,26 @@ +# -*- coding: utf-8 -*- +############################################################################### +# +# Module for OpenERP +# Copyright (C) 2014 Akretion (http://www.akretion.com). +# @author Sébastien BEAU +# +# This program is free software: you can redistribute it and/or modify +# it under the terms of the GNU Affero General Public License as +# published by the Free Software Foundation, either version 3 of the +# License, or (at your option) any later version. +# +# This program is distributed in the hope that it will be useful, +# but WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +# GNU Affero General Public License for more details. +# +# You should have received a copy of the GNU Affero General Public License +# along with this program. If not, see . +# +############################################################################### + +import attachment +import location +import task + diff --git a/external_file_location/__openerp__.py b/external_file_location/__openerp__.py new file mode 100644 index 00000000..e2b4624f --- /dev/null +++ b/external_file_location/__openerp__.py @@ -0,0 +1,46 @@ +# -*- coding: utf-8 -*- +############################################################################### +# +# Module for OpenERP +# Copyright (C) 2014 Akretion (http://www.akretion.com). +# @author Sébastien BEAU +# +# This program is free software: you can redistribute it and/or modify +# it under the terms of the GNU Affero General Public License as +# published by the Free Software Foundation, either version 3 of the +# License, or (at your option) any later version. +# +# This program is distributed in the hope that it will be useful, +# but WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +# GNU Affero General Public License for more details. +# +# You should have received a copy of the GNU Affero General Public License +# along with this program. If not, see . +# +############################################################################### + +{'name': 'external_file_location', + 'version': '0.0.1', + 'author': 'Akretion', + 'website': 'www.akretion.com', + 'license': 'AGPL-3', + 'category': 'Generic Modules', + 'description': """ + + """, + 'depends': [ + 'base', + ], + 'data': [ + 'attachment_view.xml', + 'location_view.xml', + 'task_view.xml', + ], + 'installable': True, + 'application': True, +} + + + + diff --git a/external_file_location/attachment.py b/external_file_location/attachment.py new file mode 100644 index 00000000..fc1d479e --- /dev/null +++ b/external_file_location/attachment.py @@ -0,0 +1,37 @@ +# -*- coding: utf-8 -*- +############################################################################### +# +# Module for OpenERP +# Copyright (C) 2014 Akretion (http://www.akretion.com). +# @author Sébastien BEAU +# +# This program is free software: you can redistribute it and/or modify +# it under the terms of the GNU Affero General Public License as +# published by the Free Software Foundation, either version 3 of the +# License, or (at your option) any later version. +# +# This program is distributed in the hope that it will be useful, +# but WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +# GNU Affero General Public License for more details. +# +# You should have received a copy of the GNU Affero General Public License +# along with this program. If not, see . +# +############################################################################### + +from openerp import models, fields, api, _ +from openerp.exceptions import Warning +import hashlib + + +class AttachmentMetadata(models.Model): + _inherit = 'ir.attachment' + + sync_date = fields.Datetime() + parse_state = fields.Selection([ + ('pending', 'Pending'), + ('failed', 'Failed'), + ('done', 'Done'), + ], readonly=True, required=True, default='pending') + diff --git a/external_file_location/attachment_view.xml b/external_file_location/attachment_view.xml new file mode 100644 index 00000000..69cd719e --- /dev/null +++ b/external_file_location/attachment_view.xml @@ -0,0 +1,18 @@ + + + + + + ir.attachment + + + + + + + + + + + + diff --git a/external_file_location/backend.py b/external_file_location/backend.py new file mode 100755 index 00000000..7555f125 --- /dev/null +++ b/external_file_location/backend.py @@ -0,0 +1,34 @@ +#!/usr/bin/env python +# -*- coding: utf-8 -*- + + +class AbstractConnection(object): + + def __init__(self, host, user, pwd, port=None, allow_dir_creation=False): + self.host = host + self.user = user + self.pwd = pwd + self.port = port + self.allow_dir_creation = allow_dir_creation + self.connection = None + + def connect(self): + return NotImplemented + + def close(self): + return NotImplemented + + def get(self, filename, path=None): + return NotImplemented + + def put(self, fileobject, filename, path=None): + return NotImplemented + + def search(self, filename, path=None): + return NotImplemented + + def move(self, filename, oldpath, newpath): + return NotImplemented + + def rename(self, oldfilename, newfilename, path=None): + return NotImplemented diff --git a/external_file_location/backends/.filestore.py.swp b/external_file_location/backends/.filestore.py.swp new file mode 100644 index 0000000000000000000000000000000000000000..0940500770feb6bb3b7b81a7066109dd0e57bc69 GIT binary patch literal 12288 zcmeI2J&YVR6vv&=gpUh|4@IJKHbv%OcJ~5N5)NIYB+^M&a7_*hA{cpRytk8^wI{ac zc9$q1r3rMAsA&)qD3lbm&>&GlLAp>-5Ty?t5`TL>c6019*Bpc5WvYT#8W!v{Du3vkc>wWrt>^gR3B4u}1x+-VN z=x(YaW(P4DLQl$WP!lxCwe71oxl8c=3TSW%oB}K0 zA!5D@egk*FXW&zC3ygu&M4bl{_K#4V=JR!G=80JnM&4W{JH}Xbgs%&1TbVDLRy>Kr$4;d(?4t`fZ@tx*JL9Y%H7)kdIA?oX``Ba*6m7=D`VQ1 zijHY2Xxu0lWvMoi;=0HTP5X_{w%7QB#*YO9)+ijb7Lrs2)*I`@qv6)ASl8O!#wyP= zUu~W!%1rOp^&8#mH(DJyJ!B@>BT+L7KHFEN8LN-xOvQt0h3hFp*Xds?T1m5|3f>r$ zg~Xk3XDkJ{wMX4DDhrTBikP zI?kjnkHnm9zi3Q(0-Tz&qjZsT~Gnbs)*0Ni(8C#~GxfWdP^USQRGaQ%N*Liu<<|{W>WTmu;biKYV z-YVO7_{28bQ{lp^Q>^XhlIt|y;6hIu#bUF?^p2gi%&>F9h#^3cCbmzRurKtQfx$BF z*DE=sh7WT)EiH39-NLg}Oik?6q-vD9{-!6o9M|boci-!QwOdn9akH1UUuz?&C8^k6 crS96VZ6PO)cMGk$y;O9$*roZz45T3c021e3DF6Tf literal 0 HcmV?d00001 diff --git a/external_file_location/backends/filestore.py b/external_file_location/backends/filestore.py new file mode 100755 index 00000000..febd353b --- /dev/null +++ b/external_file_location/backends/filestore.py @@ -0,0 +1,66 @@ +#!/usr/bin/env python +# -*- coding: utf-8 -*- + +from ..backend import AbstractConnection +import sys +import os +from tempfile import TemporaryFile + +class AbtractTask() + + def __init__(self, cr, uid): + + + +class FileStoreConnection(AbstractTask): + _key = "filestore" + _name = "Filestore" + _synchronize_type = None + + def __init__(self, host, user, pwd, port=None, allow_dir_creation=False): + super(FilestoreConnection, self).__init__(host, user, pwd, port, allow_dir_creation) + + def connect(self): + return NotImplemented + + def close(self): + return NotImplemented + + def get(self, filename, path=None): + if path: + filepath = "{}/{}".format(path, filename) + else: + filepath = filename + return open(filepath, 'r+b') + + def put(self, fileobject, filename, path=None): + if path: + filepath = "{}/{}".format(path, filename) + else: + filepath = filename + output = open(filepath, 'w+b') + return True + + def search(self, filename, path=None): + if path: + filepath = "{}/{}".format(path, filename) + else: + filepath = filename + connection_list_result = os.listdir(filepath) + return [x for x in connection_list_result if filename in x] + + def move(self, filename, oldpath, newpath): + os.rename( + os.path.join(oldpath, filename), + os.path.join(newpath, filename) + ) + + def rename(self, oldfilename, newfilename, path=None): + return NotImplemented + +class ImportFileStore(FileStoreConnection): + _synchronize_type = "import" + + + def run(): + diff --git a/external_file_location/backends/ftp.py b/external_file_location/backends/ftp.py new file mode 100755 index 00000000..7316b81f --- /dev/null +++ b/external_file_location/backends/ftp.py @@ -0,0 +1,58 @@ +#!/usr/bin/env python +# -*- coding: utf-8 -*- + + +import sys +import os +from tempfile import TemporaryFile +from ftplib import FTP + +class FTPConnection(object): + + def __init__(self, host, user, pwd, port=None, allow_dir_creation=False): + super(FTPConnection, self).__init__(host, user, pwd, port, allow_dir_creation) + if not port: + self.port = 21 + self.protocol = "FTP" + + def connect(self): + self.connection = FTP(self.location, self.port) + self.connection.login(self.user, self.pwd) + + def close(self): + self.connection.close() + + def get(self, filename, path=None): + if path: + filepath = "{}/{}".format(path, filename) + else: + filepath = filename + outfile = TemporaryFile('w+b') + self.connection.retrbinary('RETR ' + filepath, outfile.write) + return outfile + + def put(self, fileobject, filename, path=None): + if path: + filepath = "{}/{}".format(path, filename) + else: + filepath = filename + self.connection.storbinary('STOR ' + filepath, fileobject) + return True + + def search(self, filename, path=None): + if path: + filepath = "{}/{}".format(path, filename) + else: + filepath = filename + connection_list_result = self.connection.nlst() + return [x for x in connection_list_result if filename in x] + + + def move(self, filename, oldpath, newpath): + self.connection.rename( + os.path.join(oldpath, filename), + os.path.join(newpath, filename) + ) + + def rename(self, oldfilename, newfilename, path=None): + return NotImplemented diff --git a/external_file_location/backends/sftp.py b/external_file_location/backends/sftp.py new file mode 100755 index 00000000..4d40b896 --- /dev/null +++ b/external_file_location/backends/sftp.py @@ -0,0 +1,59 @@ +#!/usr/bin/env python +# -*- coding: utf-8 -*- + +import sys +import paramiko +import os +from tempfile import TemporaryFile + + +class SFTPConnection(AbstractConnection): + + def __init__(self, host, user, pwd, port=None, allow_dir_creation=False): + super(SFTPConnection, self).__init__(host, user, pwd, port, allow_dir_creation) + if not port: + self.port = 22 + self.protocol = "STFP" + + def connect(self): + self.ssh = paramiko.SSHClient() + self.ssh.set_missing_host_key_policy(paramiko.AutoAddPolicy()) + self.ssh.connect(self.host, self.port, self.user, self.pwd, compress=True) + self.connection = self.ssh.open_sftp() + + def close(self): + self.connection.close() + + def get(self, filename, path=None): + if path: + remotefile = "{}/{}".format(path, filename) + else: + remotefile = filename + localfile = filename + newfile = open(filename, 'w') + self.connection.getfo(remotefile, newfile) + return newfile + + def put(self, fileobject, filename, path=None): + if path: + remotefile = "{}/{}".format(path, filename) + else: + remotefile = filename + if self.allow_dir_creation: + self.connection.mkdirs(path) + oldfile = open(fileobj, 'r') + self.connection.putfo(oldfile, remotefile) + + def search(self, filename, path=None): + if path: + self.connection.chdir(path) + file_list = self.connection.listdir() + return [x for x in file_list if filename in x] + + def move(self, filename, oldpath, newpath): + self.connection.rename(os.path.join(oldpath, filename), os.path.join(newpath, filename)) + + def rename(self, oldfilename, newfilename, path=None): + if not path: + path = '' + self.connection.rename(os.path.join(path, oldfilename), os.path.join(path, newfilename)) diff --git a/external_file_location/location.py b/external_file_location/location.py new file mode 100644 index 00000000..d82ef52b --- /dev/null +++ b/external_file_location/location.py @@ -0,0 +1,39 @@ +# -*- coding: utf-8 -*- +############################################################################### +# +# Module for OpenERP +# Copyright (C) 2014 Akretion (http://www.akretion.com). +# @author Sébastien BEAU +# +# This program is free software: you can redistribute it and/or modify +# it under the terms of the GNU Affero General Public License as +# published by the Free Software Foundation, either version 3 of the +# License, or (at your option) any later version. +# +# This program is distributed in the hope that it will be useful, +# but WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +# GNU Affero General Public License for more details. +# +# You should have received a copy of the GNU Affero General Public License +# along with this program. If not, see . +# +############################################################################### + +from openerp import models, fields + +class Location(models.Model): + _name = 'ir.location' + _description = 'Description' + + name = fields.Char(string='Name') + protocol = fields.Selection(selection='_get_protocol') + address = fields.Char(string='Address') + port = fields.Integer() + login = fields.Char() + password = fields.Char() + + + def _get_protocol(self): + return [('ftp', 'FTP'), ('sftp', 'SFTP'), ('filestore', 'Filestore')] + diff --git a/external_file_location/location_view.xml b/external_file_location/location_view.xml new file mode 100644 index 00000000..c4d4ffcf --- /dev/null +++ b/external_file_location/location_view.xml @@ -0,0 +1,52 @@ + + + + + + ir.location + +
+ + + + + + + + + + + +
+
+
+ + + ir.location + + + + + + + + + + + + + + Locations + ir.actions.act_window + ir.location + form + + + + + +
+
diff --git a/external_file_location/task.py b/external_file_location/task.py new file mode 100644 index 00000000..c632ec6c --- /dev/null +++ b/external_file_location/task.py @@ -0,0 +1,48 @@ +# -*- coding: utf-8 -*- +############################################################################### +# +# Module for OpenERP +# Copyright (C) 2014 Akretion (http://www.akretion.com). +# @author Sébastien BEAU +# +# This program is free software: you can redistribute it and/or modify +# it under the terms of the GNU Affero General Public License as +# published by the Free Software Foundation, either version 3 of the +# License, or (at your option) any later version. +# +# This program is distributed in the hope that it will be useful, +# but WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +# GNU Affero General Public License for more details. +# +# You should have received a copy of the GNU Affero General Public License +# along with this program. If not, see . +# +############################################################################### + +import sys +from openerp import models, fields + +class Task(models.Model): + _name = 'ir.location.task' + _description = 'Description' + + name = fields.Char() + method = fields.Selection([ + ('ftp_import', 'FTP import'), + ('ftp_export', 'FTP export'), + ('sftp_import', 'SFTP import'), + ('sftp_export', 'SFTP export'), + ('filestore_import', 'Filestore import'), + ('filestore_export', 'Filestore export'), + ]) + filename = fields.Char() + filepath = fields.Char() + location_id = fields.Many2one('ir.location', string='Location') + + def run(self): + connection_class = ... + + method_class = getattr(sys.modules[__name__], self.method) + conn = method_class(config) + conn.run() diff --git a/external_file_location/task_view.xml b/external_file_location/task_view.xml new file mode 100644 index 00000000..b8e928b1 --- /dev/null +++ b/external_file_location/task_view.xml @@ -0,0 +1,47 @@ + + + + + + ir.location.task + +
+ + + + + + + + +
+
+
+ + + ir.location.task + + + + + + + + + + + + Tasks + ir.actions.act_window + ir.location.task + form + + + + + +
+