mirror of
https://github.com/lxsang/antos-frontend.git
synced 2024-11-16 17:48:21 +01:00
VFS for Google Drive, 1st working version
This commit is contained in:
parent
77336716b5
commit
28ab98b055
@ -304,6 +304,8 @@ class FileDiaLog extends BaseDialog
|
|||||||
|
|
||||||
(@find "bt-cancel").set "onbtclick", (e) ->
|
(@find "bt-cancel").set "onbtclick", (e) ->
|
||||||
me.quit()
|
me.quit()
|
||||||
($ filename).css("display", "block").val @data.file.basename or "Untitled" if @data and @data.file
|
if @data and @data.file
|
||||||
|
($ filename).css("display", "block").val @data.file.basename or "Untitled"
|
||||||
|
@trigger "resize"
|
||||||
|
|
||||||
this.OS.register "FileDiaLog", FileDiaLog
|
this.OS.register "FileDiaLog", FileDiaLog
|
@ -103,9 +103,11 @@ self.OS.API =
|
|||||||
.done (data) ->
|
.done (data) ->
|
||||||
_API.loaded q, p, "OK"
|
_API.loaded q, p, "OK"
|
||||||
c(data)
|
c(data)
|
||||||
|
o.remove()
|
||||||
.fail (e, s) ->
|
.fail (e, s) ->
|
||||||
_API.loaded q, p, "FAIL"
|
_API.loaded q, p, "FAIL"
|
||||||
f(e, s)
|
f(e, s)
|
||||||
|
o.remove()
|
||||||
|
|
||||||
o.click()
|
o.click()
|
||||||
|
|
||||||
|
@ -353,7 +353,7 @@ self.OS.GUI =
|
|||||||
_OS.cleanup()
|
_OS.cleanup()
|
||||||
# get setting from conf
|
# get setting from conf
|
||||||
_OS.systemSetting(conf)
|
_OS.systemSetting(conf)
|
||||||
console.log _OS.setting
|
#console.log _OS.setting
|
||||||
# load theme
|
# load theme
|
||||||
_GUI.loadTheme _OS.setting.appearance.theme
|
_GUI.loadTheme _OS.setting.appearance.theme
|
||||||
# initDM
|
# initDM
|
||||||
|
@ -60,6 +60,16 @@
|
|||||||
self.items.unshift(e)
|
self.items.unshift(e)
|
||||||
if(u) self.update()
|
if(u) self.update()
|
||||||
}
|
}
|
||||||
|
self.root.replaceItem = function(o, n, u)
|
||||||
|
{
|
||||||
|
var ix = self.items.indexOf(o)
|
||||||
|
if(ix >= 0)
|
||||||
|
{
|
||||||
|
self.items[ix] = n
|
||||||
|
if(u) self.update()
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
self.root.remove = function(e,u)
|
self.root.remove = function(e,u)
|
||||||
{
|
{
|
||||||
var i = self.items.indexOf(e)
|
var i = self.items.indexOf(e)
|
||||||
|
@ -56,6 +56,11 @@
|
|||||||
e.closable = self.closable
|
e.closable = self.closable
|
||||||
self.refs.list.root.push(e,u)
|
self.refs.list.root.push(e,u)
|
||||||
}
|
}
|
||||||
|
self.root.replaceItem = function(o,n,u)
|
||||||
|
{
|
||||||
|
n.closable = self.closable
|
||||||
|
self.refs.list.root.replaceItem(o,n,u)
|
||||||
|
}
|
||||||
self.root.unshift = function(e,u)
|
self.root.unshift = function(e,u)
|
||||||
{
|
{
|
||||||
self.refs.list.root.unshift(e,u)
|
self.refs.list.root.unshift(e,u)
|
||||||
|
@ -36,6 +36,12 @@ class BaseFileHandler
|
|||||||
|
|
||||||
isRoot: () -> (not @genealogy) or (@genealogy.size is 0)
|
isRoot: () -> (not @genealogy) or (@genealogy.size is 0)
|
||||||
|
|
||||||
|
child: (name) ->
|
||||||
|
if @isRoot()
|
||||||
|
return @path + name
|
||||||
|
else
|
||||||
|
return @path + "/" + name
|
||||||
|
|
||||||
isHidden: () ->
|
isHidden: () ->
|
||||||
return false if not @basename
|
return false if not @basename
|
||||||
@basename[0] is "."
|
@basename[0] is "."
|
||||||
@ -44,10 +50,20 @@ class BaseFileHandler
|
|||||||
return -1 unless @path
|
return -1 unless @path
|
||||||
return @path.hash()
|
return @path.hash()
|
||||||
|
|
||||||
getb64: (m) ->
|
sendB64: (m, f) ->
|
||||||
return "" unless @cache
|
me = @
|
||||||
b64 = @cache.asBase64()
|
return unless @cache
|
||||||
return "data:#{m};base64,#{b64}"
|
if typeof @cache is "string"
|
||||||
|
b64 = @cache.asBase64()
|
||||||
|
b64 = "data:#{m};base64,#{b64}"
|
||||||
|
f(b64)
|
||||||
|
else
|
||||||
|
reader = new FileReader()
|
||||||
|
reader.readAsDataURL(@cache)
|
||||||
|
reader.onload = () ->
|
||||||
|
f reader.result
|
||||||
|
reader.onerror = (e) ->
|
||||||
|
return _courrier.osfail "Cannot ecode file: #{me.path}", (_API.throwe "OS.VFS"), e
|
||||||
parent: () ->
|
parent: () ->
|
||||||
return @ if @isRoot()
|
return @ if @isRoot()
|
||||||
return (@protocol + ":///" + (@genealogy.slice 0 , @genealogy.length - 1).join "/")
|
return (@protocol + ":///" + (@genealogy.slice 0 , @genealogy.length - 1).join "/")
|
||||||
@ -140,7 +156,8 @@ class RemoteFileHandler extends self.OS.API.VFS.BaseFileHandler
|
|||||||
return f { error: "#{@path} is not a directory" } if @info.type is "file"
|
return f { error: "#{@path} is not a directory" } if @info.type is "file"
|
||||||
_API.handler.mkdir "#{@path}/#{p}", f
|
_API.handler.mkdir "#{@path}/#{p}", f
|
||||||
when "write"
|
when "write"
|
||||||
_API.handler.write @path, p, f
|
@sendB64 p, (data) ->
|
||||||
|
_API.handler.write me.path, data, f
|
||||||
when "upload"
|
when "upload"
|
||||||
return if @info.type is "file"
|
return if @info.type is "file"
|
||||||
_API.handler.upload @path, f
|
_API.handler.upload @path, f
|
||||||
|
@ -9,6 +9,7 @@ class GoogleDriveHandler extends this.OS.API.VFS.BaseFileHandler
|
|||||||
@setting = _OS.setting.VFS.gdrive
|
@setting = _OS.setting.VFS.gdrive
|
||||||
return _courrier.oserror "Unknown API setting for google drive VFS", (_API.throwe "OS.VFS"), null unless @setting
|
return _courrier.oserror "Unknown API setting for google drive VFS", (_API.throwe "OS.VFS"), null unless @setting
|
||||||
@gid = 'root' if @isRoot()
|
@gid = 'root' if @isRoot()
|
||||||
|
@cache = ""
|
||||||
|
|
||||||
oninit: (f) ->
|
oninit: (f) ->
|
||||||
me = @
|
me = @
|
||||||
@ -28,6 +29,7 @@ class GoogleDriveHandler extends this.OS.API.VFS.BaseFileHandler
|
|||||||
fn = (r) ->
|
fn = (r) ->
|
||||||
return f() if r
|
return f() if r
|
||||||
# perform the login
|
# perform the login
|
||||||
|
G_CACHE = {"gdv:///":"root"}
|
||||||
gapi.auth2.getAuthInstance().signIn()
|
gapi.auth2.getAuthInstance().signIn()
|
||||||
|
|
||||||
gapi.auth2.getAuthInstance().isSignedIn.listen (r) ->
|
gapi.auth2.getAuthInstance().isSignedIn.listen (r) ->
|
||||||
@ -65,21 +67,49 @@ class GoogleDriveHandler extends this.OS.API.VFS.BaseFileHandler
|
|||||||
|
|
||||||
fields: () ->
|
fields: () ->
|
||||||
return "webContentLink, id, name,mimeType,description, kind, parents, properties, iconLink, createdTime, modifiedTime, owners, permissions, fullFileExtension, fileExtension, size"
|
return "webContentLink, id, name,mimeType,description, kind, parents, properties, iconLink, createdTime, modifiedTime, owners, permissions, fullFileExtension, fileExtension, size"
|
||||||
|
isFolder: () ->
|
||||||
|
return @info.mimeType is "application/vnd.google-apps.folder"
|
||||||
|
|
||||||
|
save: (id, m, f) ->
|
||||||
|
me = @
|
||||||
|
user = gapi.auth2.getAuthInstance().currentUser.get()
|
||||||
|
oauthToken = user.getAuthResponse().access_token
|
||||||
|
|
||||||
|
xhr = new XMLHttpRequest()
|
||||||
|
url = 'https://www.googleapis.com/upload/drive/v3/files/' + id + '?uploadType=media'
|
||||||
|
xhr.open('PATCH', url)
|
||||||
|
xhr.setRequestHeader 'Authorization', 'Bearer ' + oauthToken
|
||||||
|
xhr.setRequestHeader 'Content-Type', m
|
||||||
|
xhr.setRequestHeader 'Content-Encoding', 'base64'
|
||||||
|
xhr.setRequestHeader 'Content-Transfer-Encoding', 'base64'
|
||||||
|
error = (e, s) ->
|
||||||
|
_courrier.oserror "VFS cannot save : #{me.path}", e, s
|
||||||
|
xhr.onreadystatechange = () ->
|
||||||
|
if ( xhr.readyState == 4 )
|
||||||
|
if ( xhr.status == 200 )
|
||||||
|
f { result: JSON.parse(xhr.responseText) }
|
||||||
|
else
|
||||||
|
error xhr, xhr.status
|
||||||
|
xhr.onerror = () ->
|
||||||
|
error xhr, xhr.status
|
||||||
|
|
||||||
|
@sendB64 m, (data) ->
|
||||||
|
xhr.send data.replace /^data:[^;]+;base64,/g, ""
|
||||||
|
|
||||||
action: (n, p, f) ->
|
action: (n, p, f) ->
|
||||||
me = @
|
me = @
|
||||||
switch n
|
switch n
|
||||||
when "read"
|
when "read"
|
||||||
return unless @info.id
|
return unless @info.id
|
||||||
if @info.mimeType is "application/vnd.google-apps.folder"
|
if @isFolder()
|
||||||
gapi.client.drive.files.list {
|
gapi.client.drive.files.list {
|
||||||
q: "'#{me.info.id}' in parents and trashed = false",
|
q: "'#{me.info.id}' in parents and trashed = false",
|
||||||
fields: "files(#{me.fields()})"
|
fields: "files(#{me.fields()})"
|
||||||
}
|
}
|
||||||
.then (r) ->
|
.then (r) ->
|
||||||
return unless r.result.files and r.result.files.length > 0
|
return unless r.result.files
|
||||||
for file in r.result.files
|
for file in r.result.files
|
||||||
file.path = me.path + "/" + file.name
|
file.path = me.child file.name
|
||||||
file.mime = file.mimeType
|
file.mime = file.mimeType
|
||||||
file.filename = file.name
|
file.filename = file.name
|
||||||
file.type = "file"
|
file.type = "file"
|
||||||
@ -87,6 +117,7 @@ class GoogleDriveHandler extends this.OS.API.VFS.BaseFileHandler
|
|||||||
if file.mimeType is "application/vnd.google-apps.folder"
|
if file.mimeType is "application/vnd.google-apps.folder"
|
||||||
file.mime = "dir"
|
file.mime = "dir"
|
||||||
file.type = "dir"
|
file.type = "dir"
|
||||||
|
file.size = 0
|
||||||
f { result: r.result.files }
|
f { result: r.result.files }
|
||||||
else
|
else
|
||||||
gapi.client.drive.files.get {
|
gapi.client.drive.files.get {
|
||||||
@ -97,19 +128,101 @@ class GoogleDriveHandler extends this.OS.API.VFS.BaseFileHandler
|
|||||||
f r.body
|
f r.body
|
||||||
|
|
||||||
when "mk"
|
when "mk"
|
||||||
|
return f { error: "#{@path} is not a directory" } unless @isFolder()
|
||||||
|
meta =
|
||||||
|
name: p,
|
||||||
|
parents: [@info.id],
|
||||||
|
mimeType: 'application/vnd.google-apps.folder'
|
||||||
|
|
||||||
|
gapi.client.drive.files.create {
|
||||||
|
resource: meta,
|
||||||
|
fields: 'id'
|
||||||
|
}
|
||||||
|
.execute (r) ->
|
||||||
|
#console.log r
|
||||||
|
return _courrier.oserror "VFS cannot create : #{p}", (_API.throwe "OS.VFS"), r unless r and r.result
|
||||||
|
G_CACHE[me.child p] = r.result.id
|
||||||
|
f r
|
||||||
|
|
||||||
return
|
return
|
||||||
|
|
||||||
when "write"
|
when "write"
|
||||||
return
|
gid = G_CACHE[me.path]
|
||||||
|
if gid
|
||||||
|
@save gid, p, f
|
||||||
|
else
|
||||||
|
console.log "New file"
|
||||||
|
dir = @parent().asFileHandler()
|
||||||
|
dir.onready () ->
|
||||||
|
meta =
|
||||||
|
name: me.basename,
|
||||||
|
mimeType: p,
|
||||||
|
parents: [dir.info.id]
|
||||||
|
|
||||||
|
gapi.client.drive.files.create {
|
||||||
|
resource: meta,
|
||||||
|
fields: 'id'
|
||||||
|
}
|
||||||
|
.execute (r) ->
|
||||||
|
return _courrier.oserror "VFS cannot write : #{me.path}", (_API.throwe "OS.VFS"), r unless r and r.result
|
||||||
|
G_CACHE[me.path] = r.result.id
|
||||||
|
me.save r.result.id, p, f
|
||||||
|
|
||||||
when "upload"
|
when "upload"
|
||||||
return
|
return unless @isFolder()
|
||||||
|
q = _courrier.getMID()
|
||||||
|
#insert a temporal file selector
|
||||||
|
o = ($ '<input>').attr('type', 'file').css("display", "none")
|
||||||
|
o.change () ->
|
||||||
|
#_API.loading q, p
|
||||||
|
fo = o[0].files[0]
|
||||||
|
file = (me.child fo.name).asFileHandler()
|
||||||
|
file.cache = fo
|
||||||
|
file.write fo.type, f
|
||||||
|
o.remove()
|
||||||
|
|
||||||
|
#_API.loaded q, p, "OK"
|
||||||
|
#_API.loaded q, p, "FAIL"
|
||||||
|
|
||||||
|
o.click()
|
||||||
|
|
||||||
when "remove"
|
when "remove"
|
||||||
return
|
return unless @info.id
|
||||||
|
gapi.client.drive.files.delete {
|
||||||
|
fileId: me.info.id
|
||||||
|
}
|
||||||
|
.execute (r) ->
|
||||||
|
#console.log r
|
||||||
|
return _courrier.oserror "VFS cannot delete : #{me.path}", (_API.throwe "OS.VFS"), r unless r
|
||||||
|
G_CACHE[me.path] = null
|
||||||
|
f { result: true }
|
||||||
|
|
||||||
when "publish"
|
when "publish"
|
||||||
return
|
return
|
||||||
|
|
||||||
when "download"
|
when "download"
|
||||||
return
|
gapi.client.drive.files.get {
|
||||||
|
fileId: me.info.id,
|
||||||
|
alt: 'media'
|
||||||
|
}
|
||||||
|
.then (r) ->
|
||||||
|
return _courrier.oserror "VFS cannot get file : #{me.path}", (_API.throwe "OS.VFS"), r unless r.body
|
||||||
|
blob = new Blob [r.body], { type: "octet/stream" }
|
||||||
|
_API.saveblob me.basename, blob
|
||||||
|
|
||||||
when "move"
|
when "move"
|
||||||
return
|
dest = p.asFileHandler().parent().asFileHandler()
|
||||||
|
dest.onready () ->
|
||||||
|
previousParents = me.info.parents.join ','
|
||||||
|
gapi.client.drive.files.update {
|
||||||
|
fileId: me.info.id,
|
||||||
|
addParents: dest.info.id,
|
||||||
|
removeParents: previousParents,
|
||||||
|
fields: "id"
|
||||||
|
}
|
||||||
|
.execute (r) ->
|
||||||
|
return _courrier.oserror "VFS cannot move : #{me.path}", (_API.throwe "OS.VFS"), r unless r
|
||||||
|
f r
|
||||||
else
|
else
|
||||||
return _courrier.osfail "VFS unknown action: #{n}", (_API.throwe "OS.VFS"), n
|
return _courrier.osfail "VFS unknown action: #{n}", (_API.throwe "OS.VFS"), n
|
||||||
|
|
||||||
|
@ -88,6 +88,7 @@ class Files extends this.OS.GUI.BaseApplication
|
|||||||
|
|
||||||
chdir: (p) ->
|
chdir: (p) ->
|
||||||
me = @
|
me = @
|
||||||
|
console.log "ch"
|
||||||
dir = if p then p.asFileHandler() else me.currdir
|
dir = if p then p.asFileHandler() else me.currdir
|
||||||
dir.read (d) ->
|
dir.read (d) ->
|
||||||
if(d.error)
|
if(d.error)
|
||||||
@ -102,7 +103,7 @@ class Files extends this.OS.GUI.BaseApplication
|
|||||||
d.result.unshift p
|
d.result.unshift p
|
||||||
($ me.navinput).val dir.path
|
($ me.navinput).val dir.path
|
||||||
me.view.set "path", dir.path
|
me.view.set "path", dir.path
|
||||||
console.log d.result
|
#console.log d.result
|
||||||
me.view.set "data", d.result
|
me.view.set "data", d.result
|
||||||
|
|
||||||
mnFile:() ->
|
mnFile:() ->
|
||||||
@ -252,7 +253,7 @@ class Files extends this.OS.GUI.BaseApplication
|
|||||||
@openDialog "PromptDialog",
|
@openDialog "PromptDialog",
|
||||||
(d) ->
|
(d) ->
|
||||||
fp = "#{me.currdir.path}/#{d}".asFileHandler()
|
fp = "#{me.currdir.path}/#{d}".asFileHandler()
|
||||||
fp.write "", (r) ->
|
fp.write "text/plain", (r) ->
|
||||||
me.error "Fail to create #{d}: #{r.error}" if r.error
|
me.error "Fail to create #{d}: #{r.error}" if r.error
|
||||||
, "New file", { label: "File name:" }
|
, "New file", { label: "File name:" }
|
||||||
|
|
||||||
|
@ -112,6 +112,7 @@ class NotePad extends this.OS.GUI.BaseApplication
|
|||||||
open: (file) ->
|
open: (file) ->
|
||||||
#find table
|
#find table
|
||||||
i = @findTabByFile file
|
i = @findTabByFile file
|
||||||
|
@fileview.set "preventUpdate", true
|
||||||
return @tabarea.set "selected", i if i isnt -1
|
return @tabarea.set "selected", i if i isnt -1
|
||||||
return @newtab file if file.path.toString() is "Untitled"
|
return @newtab file if file.path.toString() is "Untitled"
|
||||||
me = @
|
me = @
|
||||||
@ -163,7 +164,7 @@ class NotePad extends this.OS.GUI.BaseApplication
|
|||||||
|
|
||||||
save: (file) ->
|
save: (file) ->
|
||||||
me = @
|
me = @
|
||||||
file.write (file.getb64 "text/plain"), (d) ->
|
file.write "text/plain", (d) ->
|
||||||
return me.error "Error saving file #{file.basename}" if d.error
|
return me.error "Error saving file #{file.basename}" if d.error
|
||||||
file.dirty = false
|
file.dirty = false
|
||||||
file.text = file.basename
|
file.text = file.basename
|
||||||
@ -191,7 +192,6 @@ class NotePad extends this.OS.GUI.BaseApplication
|
|||||||
@currfile.selected = false
|
@currfile.selected = false
|
||||||
file.selected = true
|
file.selected = true
|
||||||
#console.log cnt
|
#console.log cnt
|
||||||
@fileview.set "preventUpdate", true
|
|
||||||
@tabarea.push file, true
|
@tabarea.push file, true
|
||||||
#@currfile = @file
|
#@currfile = @file
|
||||||
#TODO: fix problem : @tabarea.set "selected", cnt
|
#TODO: fix problem : @tabarea.set "selected", cnt
|
||||||
@ -255,7 +255,15 @@ class NotePad extends this.OS.GUI.BaseApplication
|
|||||||
me = @
|
me = @
|
||||||
saveas = () ->
|
saveas = () ->
|
||||||
me.openDialog "FileDiaLog", (d, n) ->
|
me.openDialog "FileDiaLog", (d, n) ->
|
||||||
me.currfile.setPath "#{d}/#{n}"
|
file = "#{d}/#{n}".asFileHandler()
|
||||||
|
file.cache = me.currfile.cache
|
||||||
|
file.dirty = me.currfile.dirty
|
||||||
|
file.um = me.currfile.um
|
||||||
|
file.cursor = me.currfile.cursor
|
||||||
|
file.selected = me.currfile.selected
|
||||||
|
file.text = me.currfile.text
|
||||||
|
me.tabarea.replaceItem me.currfile, file, false
|
||||||
|
me.currfile = file
|
||||||
me.save me.currfile
|
me.save me.currfile
|
||||||
, "Save as", { file: me.currfile }
|
, "Save as", { file: me.currfile }
|
||||||
switch e
|
switch e
|
||||||
|
Loading…
Reference in New Issue
Block a user