branch develop updated (0a3df04 -> e9dae2c)
This is an automated email from the git hooks/post-receive script. New change to branch develop in repository scmwebeditor. See http://git.nuiton.org/scmwebeditor.git from 0a3df04 Add the ability to save the edited file by a Ctrl-S in the editor new e9dae2c Add the ability to open image files The 1 revisions listed above as "new" are entirely new to this repository and will be described in separate emails. The revisions listed as "adds" were already present in the repository and have only been added to this reference. Detailed log of new commits: commit e9dae2c65832ffb5a04dda48703ef4bd593b3500 Author: Hugo PIGEON <hpigeon@codelutin.com> Date: Mon Jun 1 16:29:52 2015 +0200 Add the ability to open image files Summary of changes: .../org/nuiton/scmwebeditor/git/GitConnection.java | 9 + .../org/nuiton/scmwebeditor/git/GitProvider.java | 5 + .../org/nuiton/scmwebeditor/api/ScmConnection.java | 9 + .../org/nuiton/scmwebeditor/api/ScmProvider.java | 6 + .../org/nuiton/scmwebeditor/svn/SvnConnection.java | 5 + .../org/nuiton/scmwebeditor/svn/SvnProvider.java | 5 + .../scmwebeditor/uiweb/ImageBytesResult.java | 24 +- .../scmwebeditor/uiweb/actions/BrowseAction.java | 16 +- .../scmwebeditor/uiweb/actions/GetImageAction.java | 102 +++++++ .../{EditAction.java => ViewImageAction.java} | 97 ++----- .../i18n/scmwebeditor-ui-web_en_GB.properties | 3 +- .../i18n/scmwebeditor-ui-web_fr_FR.properties | 3 +- swe-ui-web/src/main/resources/struts.xml | 13 + .../src/main/webapp/WEB-INF/content/browse.jsp | 12 +- .../main/webapp/WEB-INF/content/imageViewer.jsp | 312 +++++++++++++++++++++ .../webapp/WEB-INF/content/modificationViewer.jsp | 12 +- swe-ui-web/src/main/webapp/css/main.css | 5 + swe-ui-web/src/main/webapp/js/editor.js | 4 +- 18 files changed, 537 insertions(+), 105 deletions(-) copy swe-scm-api/src/main/java/org/nuiton/scmwebeditor/api/dto/result/AbstractResultDto.java => swe-ui-web/src/main/java/org/nuiton/scmwebeditor/uiweb/ImageBytesResult.java (51%) create mode 100644 swe-ui-web/src/main/java/org/nuiton/scmwebeditor/uiweb/actions/GetImageAction.java copy swe-ui-web/src/main/java/org/nuiton/scmwebeditor/uiweb/actions/{EditAction.java => ViewImageAction.java} (71%) create mode 100644 swe-ui-web/src/main/webapp/WEB-INF/content/imageViewer.jsp -- To stop receiving notification emails like this one, please contact nuiton.org SCM administrator <admin+scm@nuiton.org>.
This is an automated email from the git hooks/post-receive script. New commit to branch develop in repository scmwebeditor. See http://git.nuiton.org/scmwebeditor.git commit e9dae2c65832ffb5a04dda48703ef4bd593b3500 Author: Hugo PIGEON <hpigeon@codelutin.com> Date: Mon Jun 1 16:29:52 2015 +0200 Add the ability to open image files --- .../org/nuiton/scmwebeditor/git/GitConnection.java | 9 + .../org/nuiton/scmwebeditor/git/GitProvider.java | 5 + .../org/nuiton/scmwebeditor/api/ScmConnection.java | 9 + .../org/nuiton/scmwebeditor/api/ScmProvider.java | 6 + .../org/nuiton/scmwebeditor/svn/SvnConnection.java | 5 + .../org/nuiton/scmwebeditor/svn/SvnProvider.java | 5 + .../scmwebeditor/uiweb/ImageBytesResult.java | 43 +++ .../scmwebeditor/uiweb/actions/BrowseAction.java | 16 +- .../scmwebeditor/uiweb/actions/GetImageAction.java | 102 +++++++ .../uiweb/actions/ViewImageAction.java | 244 ++++++++++++++++ .../i18n/scmwebeditor-ui-web_en_GB.properties | 3 +- .../i18n/scmwebeditor-ui-web_fr_FR.properties | 3 +- swe-ui-web/src/main/resources/struts.xml | 13 + .../src/main/webapp/WEB-INF/content/browse.jsp | 12 +- .../main/webapp/WEB-INF/content/imageViewer.jsp | 312 +++++++++++++++++++++ .../webapp/WEB-INF/content/modificationViewer.jsp | 12 +- swe-ui-web/src/main/webapp/css/main.css | 5 + swe-ui-web/src/main/webapp/js/editor.js | 4 +- 18 files changed, 792 insertions(+), 16 deletions(-) diff --git a/swe-git/src/main/java/org/nuiton/scmwebeditor/git/GitConnection.java b/swe-git/src/main/java/org/nuiton/scmwebeditor/git/GitConnection.java index 384c5e9..92a5e3a 100644 --- a/swe-git/src/main/java/org/nuiton/scmwebeditor/git/GitConnection.java +++ b/swe-git/src/main/java/org/nuiton/scmwebeditor/git/GitConnection.java @@ -1273,6 +1273,15 @@ public class GitConnection implements ScmConnection { return fileName; } + @Override + public String getImagePath(String address, String repositoryRoot) { + + String path = localDirectory.getAbsolutePath() + address.replace(repositoryRoot, ""); + path.replaceAll("/", File.separator); + + return path; + } + /** * Changing for another branch diff --git a/swe-git/src/main/java/org/nuiton/scmwebeditor/git/GitProvider.java b/swe-git/src/main/java/org/nuiton/scmwebeditor/git/GitProvider.java index 95ea4f0..fefa5fc 100644 --- a/swe-git/src/main/java/org/nuiton/scmwebeditor/git/GitProvider.java +++ b/swe-git/src/main/java/org/nuiton/scmwebeditor/git/GitProvider.java @@ -251,6 +251,11 @@ public class GitProvider implements ScmProvider { } @Override + public boolean filesDirectlyAccessible() { + return false; + } + + @Override public ScmConnection getConnection(String address, String pathToLocalRepos) { GitConnection gitConn = null; diff --git a/swe-scm-api/src/main/java/org/nuiton/scmwebeditor/api/ScmConnection.java b/swe-scm-api/src/main/java/org/nuiton/scmwebeditor/api/ScmConnection.java index 65010ec..542f256 100644 --- a/swe-scm-api/src/main/java/org/nuiton/scmwebeditor/api/ScmConnection.java +++ b/swe-scm-api/src/main/java/org/nuiton/scmwebeditor/api/ScmConnection.java @@ -122,4 +122,13 @@ public interface ScmConnection { * @return the name of the edited file */ String getFileName(); + + + /** + * Gives the path to use to display an image on a web page + * @param address the full address of the image on the repository + * @param repositoryRoot the address of the repository's root + * @return the path to use to display an image on a web page + */ + String getImagePath(String address, String repositoryRoot); } diff --git a/swe-scm-api/src/main/java/org/nuiton/scmwebeditor/api/ScmProvider.java b/swe-scm-api/src/main/java/org/nuiton/scmwebeditor/api/ScmProvider.java index 46bbc63..08976e6 100644 --- a/swe-scm-api/src/main/java/org/nuiton/scmwebeditor/api/ScmProvider.java +++ b/swe-scm-api/src/main/java/org/nuiton/scmwebeditor/api/ScmProvider.java @@ -77,6 +77,12 @@ public interface ScmProvider { boolean supportsPush(); /** + * Tells whether the repositories' files are directly accessible by their address + * @return true if the files are directly accessible + */ + boolean filesDirectlyAccessible(); + + /** * Gives the connection to the SCM * @param address the repository's address * @param pathToLocalRepos the folder which will be used to store one client's repositories diff --git a/swe-svn/src/main/java/org/nuiton/scmwebeditor/svn/SvnConnection.java b/swe-svn/src/main/java/org/nuiton/scmwebeditor/svn/SvnConnection.java index d8808bc..b4da898 100644 --- a/swe-svn/src/main/java/org/nuiton/scmwebeditor/svn/SvnConnection.java +++ b/swe-svn/src/main/java/org/nuiton/scmwebeditor/svn/SvnConnection.java @@ -997,6 +997,11 @@ public class SvnConnection implements ScmConnection { return fileName; } + @Override + public String getImagePath(String address, String repositoryRoot) { + return address; + } + public String getSvnRoot(String username, String password) { String repositoryRoot; diff --git a/swe-svn/src/main/java/org/nuiton/scmwebeditor/svn/SvnProvider.java b/swe-svn/src/main/java/org/nuiton/scmwebeditor/svn/SvnProvider.java index 6b3fdf4..52e73f3 100644 --- a/swe-svn/src/main/java/org/nuiton/scmwebeditor/svn/SvnProvider.java +++ b/swe-svn/src/main/java/org/nuiton/scmwebeditor/svn/SvnProvider.java @@ -81,6 +81,11 @@ public class SvnProvider implements ScmProvider { } @Override + public boolean filesDirectlyAccessible() { + return true; + } + + @Override public ScmConnection getConnection(String address, String pathToLocalRepos) { SvnConnection svnConn = null; diff --git a/swe-ui-web/src/main/java/org/nuiton/scmwebeditor/uiweb/ImageBytesResult.java b/swe-ui-web/src/main/java/org/nuiton/scmwebeditor/uiweb/ImageBytesResult.java new file mode 100644 index 0000000..25ea9e5 --- /dev/null +++ b/swe-ui-web/src/main/java/org/nuiton/scmwebeditor/uiweb/ImageBytesResult.java @@ -0,0 +1,43 @@ +/* + * #%L + * ScmWebEditor + * %% + * Copyright (C) 2009 - 2015 CodeLutin + * %% + * This program is free software: you can redistribute it and/or modify + * it under the terms of the GNU Lesser 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 General Lesser Public License for more details. + * + * You should have received a copy of the GNU General Lesser Public + * License along with this program. If not, see + * <http://www.gnu.org/licenses/lgpl-3.0.html>. + * #L% + */ +package org.nuiton.scmwebeditor.uiweb; + +import com.opensymphony.xwork2.ActionInvocation; +import com.opensymphony.xwork2.Result; +import org.apache.struts2.ServletActionContext; +import org.nuiton.scmwebeditor.uiweb.actions.GetImageAction; + +import javax.servlet.http.HttpServletResponse; + +public class ImageBytesResult implements Result { + + public void execute(ActionInvocation invocation) throws Exception { + + GetImageAction action = (GetImageAction) invocation.getAction(); + HttpServletResponse response = ServletActionContext.getResponse(); + + response.setContentType(action.getCustomContentType()); + response.getOutputStream().write(action.getCustomImageInBytes()); + response.getOutputStream().flush(); + + } +} diff --git a/swe-ui-web/src/main/java/org/nuiton/scmwebeditor/uiweb/actions/BrowseAction.java b/swe-ui-web/src/main/java/org/nuiton/scmwebeditor/uiweb/actions/BrowseAction.java index 87eccb2..70cab1d 100644 --- a/swe-ui-web/src/main/java/org/nuiton/scmwebeditor/uiweb/actions/BrowseAction.java +++ b/swe-ui-web/src/main/java/org/nuiton/scmwebeditor/uiweb/actions/BrowseAction.java @@ -198,21 +198,21 @@ public class BrowseAction extends AbstractScmWebEditorAction implements ServletR node.setTitle(file.substring(file.lastIndexOf("/") + 1)); node.setState(TreeNode.NODE_STATE_LEAF); - if (file.endsWith((".js"))) { + if (file.toLowerCase().endsWith((".js"))) { node.setIcon("ui-icon-js"); - } else if (file.endsWith(".html") || file.endsWith(".htm")) { + } else if (file.toLowerCase().endsWith(".html") || file.toLowerCase().endsWith(".htm")) { node.setIcon("ui-icon-html"); - } else if (file.endsWith(".xml")) { + } else if (file.toLowerCase().endsWith(".xml")) { node.setIcon("ui-icon-xml"); - } else if (file.endsWith(".java")) { + } else if (file.toLowerCase().endsWith(".java")) { node.setIcon("ui-icon-java"); - } else if (file.endsWith(".css")) { + } else if (file.toLowerCase().endsWith(".css")) { node.setIcon("ui-icon-css"); - } else if (file.endsWith(".rst")) { + } else if (file.toLowerCase().endsWith(".rst")) { node.setIcon("ui-icon-rst"); - } else if (file.endsWith(".tex")) { + } else if (file.toLowerCase().endsWith(".tex")) { node.setIcon("ui-icon-tex"); - } else if (file.endsWith(".txt")) { + } else if (file.toLowerCase().endsWith(".txt")) { node.setIcon("ui-icon-txt"); } else { node.setIcon("ui-icon-document"); diff --git a/swe-ui-web/src/main/java/org/nuiton/scmwebeditor/uiweb/actions/GetImageAction.java b/swe-ui-web/src/main/java/org/nuiton/scmwebeditor/uiweb/actions/GetImageAction.java new file mode 100644 index 0000000..65537d4 --- /dev/null +++ b/swe-ui-web/src/main/java/org/nuiton/scmwebeditor/uiweb/actions/GetImageAction.java @@ -0,0 +1,102 @@ +/* + * #%L + * ScmWebEditor + * %% + * Copyright (C) 2009 - 2015 CodeLutin + * %% + * This program is free software: you can redistribute it and/or modify + * it under the terms of the GNU Lesser 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 General Lesser Public License for more details. + * + * You should have received a copy of the GNU General Lesser Public + * License along with this program. If not, see + * <http://www.gnu.org/licenses/lgpl-3.0.html>. + * #L% + */ +package org.nuiton.scmwebeditor.uiweb.actions; + +import org.apache.commons.logging.Log; +import org.apache.commons.logging.LogFactory; +import org.apache.struts2.interceptor.ServletRequestAware; + +import javax.imageio.ImageIO; +import javax.servlet.http.HttpServletRequest; +import java.awt.image.BufferedImage; +import java.io.ByteArrayOutputStream; +import java.io.File; +import java.io.IOException; + +/** + * Gets the image at the given path + */ +public class GetImageAction extends ScmWebEditorMainAction implements ServletRequestAware { + + private static final Log log = LogFactory.getLog(GetImageAction.class); + + protected byte[] imageInByte = null; + + protected String imagePath; + + protected HttpServletRequest servletRequest; + + + public byte[] getImageInByte() { return imageInByte; } + + public void setImageInByte(byte[] imageInByte) { this.imageInByte = imageInByte; } + + public String getImagePath() { return imagePath; } + + public void setImagePath(String imagePath) { this.imagePath = imagePath; } + + + public String execute() { + return SUCCESS; + } + + public byte[] getCustomImageInBytes() { + + BufferedImage originalImage; + + try { + File fileImage = new File(imagePath); + originalImage = ImageIO.read(fileImage); + + ByteArrayOutputStream baos = new ByteArrayOutputStream(); + ImageIO.write(originalImage, imagePath.substring(imagePath.length() - 3), baos); + baos.flush(); + imageInByte = baos.toByteArray(); + baos.close(); + } catch (IOException e) { + if (log.isErrorEnabled()) { + log.error("Can not get image file at " + imagePath, e); + } + } + + return imageInByte; + } + + public String getCustomContentType() { + + String type = "image/jpeg"; + String path = imagePath.toLowerCase(); + + if (path.endsWith(".png")) { + type = "image/png"; + } else if(path.endsWith(".gif")) { + type = "image/gif"; + } + + return type; + } + + @Override + public void setServletRequest(HttpServletRequest request) { + servletRequest = request; + } +} diff --git a/swe-ui-web/src/main/java/org/nuiton/scmwebeditor/uiweb/actions/ViewImageAction.java b/swe-ui-web/src/main/java/org/nuiton/scmwebeditor/uiweb/actions/ViewImageAction.java new file mode 100644 index 0000000..a6ea51f --- /dev/null +++ b/swe-ui-web/src/main/java/org/nuiton/scmwebeditor/uiweb/actions/ViewImageAction.java @@ -0,0 +1,244 @@ +/* + * #%L + * ScmWebEditor + * %% + * Copyright (C) 2009 - 2015 CodeLutin + * %% + * This program is free software: you can redistribute it and/or modify + * it under the terms of the GNU Lesser 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 General Lesser Public License for more details. + * + * You should have received a copy of the GNU General Lesser Public + * License along with this program. If not, see + * <http://www.gnu.org/licenses/lgpl-3.0.html>. + * #L% + */ +package org.nuiton.scmwebeditor.uiweb.actions; + +import org.apache.commons.logging.Log; +import org.apache.commons.logging.LogFactory; +import org.apache.shiro.codec.Base64; +import org.apache.shiro.crypto.BlowfishCipherService; +import org.nuiton.scmwebeditor.api.OperationNotSupportedException; +import org.nuiton.scmwebeditor.api.ScmConnection; +import org.nuiton.scmwebeditor.api.ScmProvider; +import org.nuiton.scmwebeditor.api.dto.result.AbstractResultDto; +import org.nuiton.scmwebeditor.uiweb.ScmWebEditorConfig; + +import javax.naming.AuthenticationException; +import javax.servlet.http.Cookie; +import javax.servlet.http.HttpSession; +import java.io.File; +import java.text.Normalizer; + +/** + * Allows to view an image + */ +public class ViewImageAction extends ScmWebEditorMainAction { + + private static final Log log = LogFactory.getLog(ViewImageAction.class); + + protected final String VIEW_IMAGE = "viewImage"; + + /** the name of the selected branch */ + protected String selectedBranch; + + /** equals true if the SCM is able to use branches */ + protected boolean scmSupportsBranches; + + /** the full path to the root of the repository */ + protected String repositoryRoot; + + /** the path to use to get the image displayed in a web page */ + protected String imagePath; + + /** equals true if the repository's files are directly accessible using their address */ + protected boolean filesDirectlyAccessible; + + + public String getSelectedBranch() { return selectedBranch; } + + public void setSelectedBranch(String selectedBranch) { this.selectedBranch = selectedBranch; } + + public boolean isScmSupportsBranches() { return scmSupportsBranches; } + + public void setScmSupportsBranches(boolean scmSupportsBranches) { this.scmSupportsBranches = scmSupportsBranches; } + + public String getRepositoryRoot() { return repositoryRoot; } + + public void setRepositoryRoot(String repositoryRoot) { this.repositoryRoot = repositoryRoot; } + + public String getImagePath() { return imagePath; } + + public void setImagePath(String imagePath) { this.imagePath = imagePath; } + + public boolean isFilesDirectlyAccessible() { return filesDirectlyAccessible; } + + public void setFilesDirectlyAccessible( + boolean filesDirectlyAccessible) { this.filesDirectlyAccessible = filesDirectlyAccessible; } + + /** + * Execution of the view image action + * @return a code interpreted in the file struts.xml + */ + public String execute() { + + HttpSession session = request.getSession(); + String sessionId = session.getId(); + + String pathToLocalRepos = ScmWebEditorConfig.getLocalRepositoriesPath() + File.separator + sessionId; + + ScmProvider provider = ScmWebEditorConfig.getProvider(scmType); + ScmConnection scmConn = provider.getConnection(address, pathToLocalRepos); + + scmSupportsBranches = provider.supportsBranches(); + filesDirectlyAccessible = provider.filesDirectlyAccessible(); + + // if the repository is not protected, we get its UUID + String repositoryUUID = scmConn.getRepositoryId(); + if (repositoryUUID == null) { + repositoryUUID = address.replace(' ', '_'); + repositoryUUID = Normalizer.normalize(repositoryUUID, Normalizer.Form.NFD).replaceAll("[\u0300-\u036F]", ""); + } + + if (repositoryRoot == null) { + repositoryRoot = address.substring(0, address.lastIndexOf('/')); + } else if (repositoryRoot.equals("")) { + repositoryRoot = address.substring(0, address.lastIndexOf('/')); + } + + if (log.isDebugEnabled()) { + log.debug("Login : " + username); + } + + + /* + * Reading the cookie + */ + + + String usernamepwCookie = null; + // read the cookies + + BlowfishCipherService bf = new BlowfishCipherService(); + + byte[] privateKey = Base64.decode(ScmWebEditorConfig.getKey()); + + if (request.getCookies() != null) { + for (Cookie c : request.getCookies()) { + if (c.getName().equals(repositoryUUID)) { + usernamepwCookie = c.getValue(); + } + } + } + + if (usernamepwCookie != null) { + + String usernameDecode = new String(bf.decrypt(Base64.decode(usernamepwCookie), privateKey).getBytes()); + + String[] resCookie = usernameDecode.split(","); + if (resCookie.length == 2) { + username = resCookie[0]; + pw = resCookie[1]; + } + } + + if (saveCookie) { + if (username != null && pw != null) { + + if (!username.equals("") && !pw.equals("")) { + Cookie authCookie = new Cookie(repositoryUUID, bf.encrypt((username + "," + pw).getBytes(), privateKey).toBase64()); + authCookie.setMaxAge(60 * 60 * 24 * 365); + response.addCookie(authCookie); + } + } + + } + + // authentication + String[] usernamePw = getUsernamePwFromSession(repositoryUUID, username, pw); + username = usernamePw[0]; + pw = usernamePw[1]; + + String name = username; + String password = pw; + + if (name == null) { + name = "anonymous"; + } + if (password == null) { + password = "anonymous"; + } + + String changeBranchError = null; + + if (scmSupportsBranches) { + try { + changeBranchError = provider.changeBranch(selectedBranch, pathToLocalRepos, username, pw); + } catch (OperationNotSupportedException e) { + if (log.isErrorEnabled()) { + log.error("Can not change branch with SCM '" + scmType + "'"); + } + } + } + + if (changeBranchError != null) { + if (changeBranchError.equals(AbstractResultDto.AUTH_ERROR)) { + return LOGIN; + } else { + return ERROR_PATH; + } + } + + + /* + * Getting the file's revision + */ + + try { + numRevision = scmConn.getHeadRevisionNumber(address, name, password); + } catch (AuthenticationException e) { + request.setAttribute(PARAMETER_ADDRESS, address); + + // if scm authentication failed user is redirected on login page + if (log.isDebugEnabled()) { + log.debug("Auth Fail ", e); + } + + // deleting the cookies for this repository + for (Cookie c : request.getCookies()) { + if (c.getName().equals(repositoryUUID)) { + c.setMaxAge(0);//On supprime le cookie + response.addCookie(c); + if (log.isDebugEnabled()) { + log.debug("Cookie supprimé"); + } + } + } + + getScmSession().delScmUser(repositoryUUID); + //redirect to a login page + return LOGIN; + } catch (IllegalArgumentException e) { + if (log.isErrorEnabled()) { + log.error("The file does not exist", e); + } + return ERROR_PATH; + } + + imagePath = scmConn.getImagePath(address, repositoryRoot); + + + if (log.isInfoEnabled()) { + log.info("IP client : " + request.getRemoteAddr() + " , get file : " + address + ". File's mimetype : " + mimeType); + } + + return VIEW_IMAGE; + } +} diff --git a/swe-ui-web/src/main/resources/i18n/scmwebeditor-ui-web_en_GB.properties b/swe-ui-web/src/main/resources/i18n/scmwebeditor-ui-web_en_GB.properties index 384ebf8..1ebc305 100644 --- a/swe-ui-web/src/main/resources/i18n/scmwebeditor-ui-web_en_GB.properties +++ b/swe-ui-web/src/main/resources/i18n/scmwebeditor-ui-web_en_GB.properties @@ -21,6 +21,7 @@ scm.createDirectorySuccess=Directory created successfully scm.createDirectoryTitle=Create a new directory on the repository scm.destinationDirectory=Destination directory\: scm.directoryToRemove=Directory to remove\: +scm.displayedImage=Displayed image\: scm.exit=Exit scm.exitJavascript=Exit ScmWebEditor? scm.exitJavascriptChanges=Exit ScmWebEditor without saving? All modification will be lost. @@ -40,7 +41,7 @@ scm.logoutWait=Logout... scm.modificationViewer.betterUseJavascript=For a better use of SCMWebEditor please activate JavaScript. scm.modificationViewer.branch=Working on branch\: scm.modificationViewer.commitOnly=Make a commit only (no push) -scm.modificationViewer.noJavascript=Javascript is not activated. You can't only use Save and Quit or upload button. +scm.modificationViewer.noJavascript=Javascript is not activated. You can only use save and quit, quit, upload a file, remove a file, Create a directory, remove a directory or move a file. scm.modificationViewer.previewPosition=Preview's position\: scm.modificationViewer.previewPosition.below=Below scm.modificationViewer.previewPosition.none=No preview diff --git a/swe-ui-web/src/main/resources/i18n/scmwebeditor-ui-web_fr_FR.properties b/swe-ui-web/src/main/resources/i18n/scmwebeditor-ui-web_fr_FR.properties index 59bf203..ff4cf2f 100644 --- a/swe-ui-web/src/main/resources/i18n/scmwebeditor-ui-web_fr_FR.properties +++ b/swe-ui-web/src/main/resources/i18n/scmwebeditor-ui-web_fr_FR.properties @@ -21,6 +21,7 @@ scm.createDirectorySuccess=Répertoire créé avec succès scm.createDirectoryTitle=Créer un nouveau répertoire sur le dépôt scm.destinationDirectory=Répertoire de destination \: scm.directoryToRemove=Répertoire à supprimer \: +scm.displayedImage=Image affichée \: scm.exit=Quitter scm.exitJavascript=Quitter ScmWebEditor ? scm.exitJavascriptChanges=Quitter ScmWebEditor sans sauvegarder ? Toutes les modifications seront perdues. @@ -40,7 +41,7 @@ scm.logoutWait=Déconnexion... scm.modificationViewer.betterUseJavascript=Activer Javascript pour accéder à toutes les fonctionnalités. scm.modificationViewer.branch=Vous travaillez sur la branche \: scm.modificationViewer.commitOnly=Faire un commit seulement (pas de push) -scm.modificationViewer.noJavascript=Javascript est désactivé. Vous pouvez seulement utiliser les boutons sauvegarder et quitter, quitter ou ajouter un fichier. +scm.modificationViewer.noJavascript=Javascript est désactivé. Vous pouvez seulement utiliser les boutons sauvegarder et quitter, quitter, ajouter un fichier, supprimer un fichier, créer un répertoire, supprimer un répertoire ou déplacer un fichier. scm.modificationViewer.previewPosition=Position de l'aperçu \: scm.modificationViewer.previewPosition.below=En dessous scm.modificationViewer.previewPosition.none=Pas d'aperçu diff --git a/swe-ui-web/src/main/resources/struts.xml b/swe-ui-web/src/main/resources/struts.xml index e7034d4..ec640c5 100644 --- a/swe-ui-web/src/main/resources/struts.xml +++ b/swe-ui-web/src/main/resources/struts.xml @@ -41,6 +41,7 @@ <result-types> <result-type name="json" class="org.apache.struts2.json.JSONResult"/> + <result-type name="imageResult" class="org.nuiton.scmwebeditor.uiweb.ImageBytesResult"/> </result-types> <interceptors> @@ -75,6 +76,18 @@ <result name="errorPath" >/WEB-INF/content/badFileRedirect.jsp</result> <result name="editPage" >/WEB-INF/content/modificationViewer.jsp</result> </action> + + <action name="viewImage" class="org.nuiton.scmwebeditor.uiweb.actions.ViewImageAction"> + <result name="noParameter" >/WEB-INF/content/outConnection.jsp</result> + <result name="login" >/WEB-INF/content/privateScmRedirect.jsp</result> + <result name="errorPath" >/WEB-INF/content/badFileRedirect.jsp</result> + <result name="viewImage" >/WEB-INF/content/imageViewer.jsp</result> + </action> + + <action name="getImage" class="org.nuiton.scmwebeditor.uiweb.actions.GetImageAction"> + <result name="success" type="imageResult"> + </result> + </action> <action name="commit" class="org.nuiton.scmwebeditor.uiweb.actions.ScmWebEditorCommitAction"> <result name="success" >/WEB-INF/content/redirect.jsp</result> diff --git a/swe-ui-web/src/main/webapp/WEB-INF/content/browse.jsp b/swe-ui-web/src/main/webapp/WEB-INF/content/browse.jsp index 804aaaa..0c62a7d 100644 --- a/swe-ui-web/src/main/webapp/WEB-INF/content/browse.jsp +++ b/swe-ui-web/src/main/webapp/WEB-INF/content/browse.jsp @@ -42,9 +42,17 @@ var scmType = document.getElementById("scmType").value; var selectedBranch = $("#selectedBranchDisplay").text().trim(); var repositoryRoot = document.getElementById("addressInput").value; + var fileExtension = item.attr("id").substr(item.attr("id").lastIndexOf(".") + 1); + var actionFile = "edit.action"; - document.location.href = ("edit.action?address=" + item.attr("id") + "&scmType=" + scmType - + "&selectedBranch=" + selectedBranch + "&repositoryRoot=" + repositoryRoot); + var supportedImages = ["jpg", "jpeg", "png", "gif"]; + + if (supportedImages.indexOf(fileExtension.toLowerCase()) != -1) { + actionFile = "viewImage.action"; + } + + document.location.href = (actionFile + "?address=" + item.attr("id") + "&scmType=" + scmType + + "&selectedBranch=" + selectedBranch + "&repositoryRoot=" + repositoryRoot); } } diff --git a/swe-ui-web/src/main/webapp/WEB-INF/content/imageViewer.jsp b/swe-ui-web/src/main/webapp/WEB-INF/content/imageViewer.jsp new file mode 100644 index 0000000..445f6da --- /dev/null +++ b/swe-ui-web/src/main/webapp/WEB-INF/content/imageViewer.jsp @@ -0,0 +1,312 @@ +<%-- + #%L + ScmWebEditor + %% + Copyright (C) 2009 - 2015 CodeLutin + %% + This program is free software: you can redistribute it and/or modify + it under the terms of the GNU Lesser 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 General Lesser Public License for more details. + + You should have received a copy of the GNU General Lesser Public + License along with this program. If not, see + <http://www.gnu.org/licenses/lgpl-3.0.html>. + #L% + --%> + +<%@page contentType="text/html" pageEncoding="UTF-8" %> +<%@ taglib prefix="s" uri="/struts-tags" %> +<%@ taglib prefix="sj" uri="/struts-jquery-tags" %> +<%@ taglib prefix="sjt" uri="/struts-jquery-tree-tags" %> +<sj:head jquerytheme="default"/> + +<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" +"http://www.w3.org/TR/html4/loose.dtd"> +<html> +<head> + <title><s:text name="scm.titles.swe"/></title> + <meta http-equiv="Content-Type" content="text/html; charset=UTF-8"/> + <script type="text/javascript" src="js/selectLanguage.js"></script> + + <script src="js/cancelRedirect.js" type="text/javascript"></script> + <script src="js/popup.js" type="text/javascript"></script> + + <link rel="icon" href="img/machine-a-ecrire_little.png" type="image/png"> + <link rel="stylesheet" type="text/css" href="css/main.css"> + + <script type="text/javascript" src="js/editor.js"></script> + + <script type="text/javascript"> + // Opens the selected file in the tree + $.subscribe('treeClicked', function(event, data) { + var item = event.originalEvent.data.rslt.obj; + + if (item.length == 1) { + var classAttr = item[0].getAttribute("class"); + + if (classAttr.contains("jstree-leaf")) { + var scmType = document.getElementById("scmType").value; + var fileExtension = item.attr("id").substr(item.attr("id").lastIndexOf(".") + 1); + var actionFile = "edit.action"; + + var supportedImages = ["jpg", "jpeg", "png", "gif"]; + + if (supportedImages.indexOf(fileExtension.toLowerCase()) != -1) { + actionFile = "viewImage.action"; + } + + document.location.href = (actionFile + "?address=" + item.attr("id") + "&scmType=" + scmType + + '&selectedBranch=<s:property value="selectedBranch"/>&repositoryRoot=<s:property value="repositoryRoot"/>'); + } + } + + }); + </script> + +</head> +<body> + +<div id="wrapper"> + + +<s:hidden name="scmType" id="scmType" value="%{scmType}"/> + +<div id="head"> + + +<div id="flagEdit"> + + <ul class="flags"> + <li> + <s:if + test="%{#session['WW_TRANS_I18N_LOCALE'] != null && #session['WW_TRANS_I18N_LOCALE'].language == 'en'}"> + <img src="img/flag-i18n-uk.png"/> + </s:if> + <s:else> + <s:a action="edit.action" namespace="/"> + <s:param name="address"><s:property value="address"/></s:param> + <s:param name="scmType"><s:property value="scmType"/></s:param> + <s:param name="selectedBranch"><s:property value="selectedBranch"/></s:param> + <s:param name="repositoryRoot"><s:property value="repositoryRoot"/></s:param> + <s:param name="request_locale">en_GB</s:param> + <img src="img/flag-i18n-uk.png"/> + </s:a> + </s:else> + </li> + <li> + <s:if + test="%{#session['WW_TRANS_I18N_LOCALE'] == null || #session['WW_TRANS_I18N_LOCALE'].language == 'fr'}"> + <img src="img/flag-i18n-fr.png"/> + </s:if> + <s:else> + <s:a action="edit.action" namespace="/"> + <s:param name="address"><s:property value="address"/></s:param> + <s:param name="scmType"><s:property value="scmType"/></s:param> + <s:param name="selectedBranch"><s:property value="selectedBranch"/></s:param> + <s:param name="repositoryRoot"><s:property value="repositoryRoot"/></s:param> + <s:param name="request_locale">fr_FR</s:param> + <img src="img/flag-i18n-fr.png"/> + </s:a> + </s:else> + </li> + + </ul> + +</div> + + +<!-- <a title="ScmWebEditor Project Website" target="_blank" href="http://maven-site.nuiton.org/scmwebeditor/"><img width="200" height="160" src="img/editor/machine-a-ecrire.png" alt="ScmWebEditor logo"/></a> --> + +<h1 id="editorTitle">SCMWebEditor</h1> + +<s:set id="openAnotherFile"> + <s:text name="scm.openAnotherFile"/> +</s:set> + +<s:submit id="openAnotherFile" value="%{openAnotherFile}" onclick="openPopin('openFilePopin'); return false;"/> + + <div id="buttonList"> + + <!-- BEGIN exit --> + + <s:if test="projectUrl != null"> + <s:hidden key="projectUrl" label=''/> + </s:if> + <s:else> + <s:hidden id="projectUrl" value="checkout.action"/> + </s:else> + + + <s:set id="scm.exitTitle"> + <s:text name="scm.exitTitle"/> + </s:set> + <s:set id="scm.exitJavascript"> + <s:text name="scm.exitJavascript"/> + </s:set> + + <s:a + href="checkout.action" + title="%{scm.exitTitle}" + value="%{scm.exit}" + name="Cancel"> + <div id="exitButton"></div> + </s:a> + + <!-- END exit --> + + </div> + + <!-- Buttons for the actions on the repository --> + + <s:set id="scm.upload"> + <s:text name="scm.upload"/> + </s:set> + <s:set id="scm.uploadTitle"> + <s:text name="scm.uploadTitle"/> + </s:set> + + <s:set id="scm.removeFile"> + <s:text name="scm.removeFile"/> + </s:set> + <s:set id="scm.removeFileTitle"> + <s:text name="scm.removeFileTitle"/> + </s:set> + + <s:set id="scm.createDirectory"> + <s:text name="scm.createDirectory"/> + </s:set> + <s:set id="scm.createDirectoryTitle"> + <s:text name="scm.createDirectoryTitle"/> + </s:set> + + <s:set id="scm.removeDirectory"> + <s:text name="scm.removeDirectory"/> + </s:set> + <s:set id="scm.removeDirectoryTitle"> + <s:text name="scm.removeDirectoryTitle"/> + </s:set> + + <s:set id="scm.moveFile"> + <s:text name="scm.moveFile"/> + </s:set> + <s:set id="scm.moveFileTitle"> + <s:text name="scm.moveFileTitle"/> + </s:set> + + <s:set name="address"> + <s:property value="address"/> + </s:set> + + <ul id="repositoryButtons"> + <li> + <s:submit name="uploadButton" value="%{scm.upload}" title="%{scm.uploadTitle}" + onClick="javascript:open_popup('doUploadFile.action', 'upload', getElementById('address').value, '%{scmType}'); return false;"/> + </li> + <li> + <s:submit name="removeButton" value="%{scm.removeFile}" title="%{scm.removeFileTitle}" + onClick="javascript:open_popup('doRemoveFile.action', 'remove', getElementById('address').value, '%{scmType}'); return false;"/> + </li> + <li> + <s:submit name="createDirectoryButton" value="%{scm.createDirectory}" title="%{scm.createDirectoryTitle}" + onClick="javascript:open_popup('doCreateDirectory.action', 'create directory',getElementById('address').value,'%{scmType}'); return false;"/> + </li> + <li> + <s:submit name="removeDirectoryButton" value="%{scm.removeDirectory}" title="%{scm.removeDirectoryTitle}" + onClick="javascript:open_popup('doRemoveDirectory.action', 'remove directory',getElementById('address').value,'%{scmType}'); return false;"/> + </li> + <li> + <s:submit name="moveFileButton" value="%{scm.moveFile}" title="%{scm.moveFileTitle}" + onClick="javascript:open_popup('doMoveFile.action', 'move file',getElementById('address').value,'%{scmType}'); return false;"/> + </li> + </ul> + +</div> + +<div id="editBody"> + + <p> + <s:text name="scm.displayedImage"/> <s:property value="address"/> + <s:text name="scm.atRevision"/> <span id="numrevisionDiv"><s:property + value="numRevision"/></span> + + <s:if test="scmSupportsBranches"> + <br/> + <s:text name="scm.modificationViewer.branch"/> <s:property value="selectedBranch"></s:property> + </s:if> + </p> + + <s:if test="filesDirectlyAccessible"> + + <img src="<s:property value="imagePath"/>" id="displayedImage"/> + + </s:if> + <s:else> + + <s:set id="imagePath"> + <s:property value="imagePath"/> + </s:set> + <img src="<s:url action='getImage.action?imagePath=%{imagePath}'/>" id="displayedImage"/> + + </s:else> + + <noscript><h4><s:text name="scm.modificationViewer.noJavascript"/></h4> + </noscript> + <noscript><h4><s:text name="scm.modificationViewer.betterUseJavascript"/></h4> + </noscript> + + <div id="form"> + + <p> + + <s:hidden key="address" label=''/> + <s:hidden key="origText" label=''/> + <s:hidden key="scmEditorUrl" label=''/> + <s:hidden key="selectedBranch" label=''/> + <s:hidden key="repositoryRoot" label=''/> + + <div id="scmButton"></div> + + </div> +</div> + + <div id="targetContentUpload"></div> + + </div> + <p align="right">©2004-2015 CodeLutin</p> + +</div> + +<!-- popin to open another file --> +<div class="popin" id="openFilePopin"> + <span class="closePopin" onclick="closePopin('openFilePopin')"> + X + </span> + + <h1><s:text name="scm.openAnotherFile"/></h1> + + <div id="searchTree"> + + <s:url id="searchTreeUrl" + action="browse?address=%{repositoryRoot}&username=%{username}&pw=%{pw}&selectedBranch=%{selectedBranch}&scmType=%{scmType}"/> + <sjt:tree id="scmTree" + htmlTitles="true" + jstreetheme="classic" + href="%{searchTreeUrl}" + onClickTopics="treeClicked" + onSuccessTopics="treeChanged" + /> + + </div> + +</div> + +<div id="popinBackground"></div> + +</body> +</html> diff --git a/swe-ui-web/src/main/webapp/WEB-INF/content/modificationViewer.jsp b/swe-ui-web/src/main/webapp/WEB-INF/content/modificationViewer.jsp index 957734a..3fc4c5e 100644 --- a/swe-ui-web/src/main/webapp/WEB-INF/content/modificationViewer.jsp +++ b/swe-ui-web/src/main/webapp/WEB-INF/content/modificationViewer.jsp @@ -108,14 +108,24 @@ if (classAttr.contains("jstree-leaf")) { var scmType = document.getElementById("scmType").value; + var fileExtension = item.attr("id").substr(item.attr("id").lastIndexOf(".") + 1); + var actionFile = "edit.action"; - document.location.href = ("edit.action?address=" + item.attr("id") + "&scmType=" + scmType + var supportedImages = ["jpg", "jpeg", "png", "gif"]; + + if (supportedImages.indexOf(fileExtension.toLowerCase()) != -1) { + actionFile = "viewImage.action"; + } + + document.location.href = (actionFile + "?address=" + item.attr("id") + "&scmType=" + scmType + '&selectedBranch=<s:property value="selectedBranch"/>&repositoryRoot=<s:property value="repositoryRoot"/>'); } } }); + window.onbeforeunload = confirmExitOnUnload; + </script> <script type="text/javascript" src="js/editor.js"></script> diff --git a/swe-ui-web/src/main/webapp/css/main.css b/swe-ui-web/src/main/webapp/css/main.css index 3497678..5ae4a10 100644 --- a/swe-ui-web/src/main/webapp/css/main.css +++ b/swe-ui-web/src/main/webapp/css/main.css @@ -476,4 +476,9 @@ ul#repositoryButtons li { .jstree { background: #FFF none repeat scroll 0% 0%; +} + +#displayedImage { + display: block; + margin: auto; } \ No newline at end of file diff --git a/swe-ui-web/src/main/webapp/js/editor.js b/swe-ui-web/src/main/webapp/js/editor.js index f1e05b1..2d9db58 100644 --- a/swe-ui-web/src/main/webapp/js/editor.js +++ b/swe-ui-web/src/main/webapp/js/editor.js @@ -39,6 +39,4 @@ $.subscribe('treeChanged', function(event, data) { children.item('ins').click(); } } -}); - -window.onbeforeunload = confirmExitOnUnload; \ No newline at end of file +}); \ No newline at end of file -- To stop receiving notification emails like this one, please contact nuiton.org SCM administrator <admin+scm@nuiton.org>.
participants (1)
-
nuiton.org scm