Avatar billede kkaen Nybegynder
05. juli 2010 - 15:22 Der er 44 kommentarer og
1 løsning

Login-funktionalitet i Netbeans

Jeg har fulgt vejledning på
http://www.roseindia.net/mysql/loginauthentication.shtml
og
http://netbeans.org/kb/docs/web/security-webapps.html#loginform

I min implementering af eksemplerne har jeg en "klient"- og "admin"-jsp-side. Disse har jeg (efter fortolkning af vejledningerne) lagt ind i henholdvis "admin"- og "klient"-bibliotekket i mit Netbeans-projekt.
Udenfor disse bibliotekker har jeg login.jsp. Login.jsp benytter en servlet til at verificere brugeren.

Jeg kan godt se login-siden. Jeg kan også logge ind både som klient og admin. Når en bruger er logget ind, har jeg brugt følgende kode til at redirecte brugeren:

out.println("Vellykket login "+studentName);

out.print("<form name=\"redirect\">\n");
out.print("<center>\n");
out.print("<font face=\"Arial\"><b>Du vil blive sendt videre i systemet om:<br><br>\n");
out.print("<form>\n");
out.print("<input type=\"text\" size=\"3\" name=\"redirect2\">\n");
out.print("</form>\n");
out.print("sekunder</b></font>\n");
out.print("</center>\n");

out.print("<script>\n");
out.print("<!--\n");

out.print("/*\n");
out.print("Count down then redirect script\n");
out.print("By JavaScript Kit (http://javascriptkit.com)\n");
out.print("Over 400+ free scripts here!\n");
out.print("*/\n");

out.print("//change below target URL to your own\n");
out.print("var targetURL=\"klient/klient.jsp\"\n");
out.print("//change the second to start counting down from\n");
out.print("var countdownfrom=3\n");

out.print("var currentsecond=document.redirect.redirect2.value=countdownfrom+1\n");
out.print("function countredirect(){\n");
out.print("if (currentsecond!=1){\n");
out.print("currentsecond-=1\n");
                out.print("document.redirect.redirect2.value=currentsecond\n");
out.print("}\n");
out.print("else{\n");
out.print("window.location=targetURL\n");
out.print("return\n");
out.print("}\n");
out.print("setTimeout(\"countredirect()\",1000)\n");
out.print("}\n");

out.print("countredirect()\n");
out.print("//-->\n");
out.print("</script>\n");

Resultatet af loginet (altså den genererede html fra det ovenstående) vises rigtigt nok. Men når der så redirektes, så kommer man bare tilbage til login-siden.

Hvis jeg prøver, at åbne klient-siden direkte inde fra Netbeans, så kommer login-siden også frem. Jeg kan altså ikke komme derhen, hvor loginet gerne skulle lede mig.

Jeg går ud fra, at det er noget med de angivne parametre inde i web.xml, som jeg har angivet ud fra vejledningen tidligere nævnt.
Men hvor har jeg lavet en fejl i forhold til min gennemgang her og vejlednings-eksemplet?
Avatar billede arne_v Ekspert
05. juli 2010 - 17:44 #1
De to link du giver er to forskellige og inkompatible løsninger.

Den ene viser app managed login.

Den anden vise container managed login.

Hvilken af dem vil du have?
Avatar billede kkaen Nybegynder
05. juli 2010 - 21:29 #2
Ah, hvis jeg har misforstået sammenhængen, så er dét jo nok noget af forklaringen :-)

Jeg ønsker en side, hvor en bruger kan logge ind. Brugere kan tilhøre 2 forskellige grupper, som har adgang til nogle bestemte jsp-sider ud fra deres login.

Jeg går ud fra, at løsningen på
http://netbeans.org/kb/docs/web/security-webapps.html#loginform
er den mest aktuelle (?)

For mange år siden fik jeg en løsning op at køre. Men teknologien er muligvis fornyet, og jeg kan heller ikke helt huske fremgangs-metoden. Hvad jeg husker, var dog, at brugerne vist blev angivet inde i en web.xml, og bibliotekerne blev også angivet herinde. Faktisk meget lignende det eksempel, jeg har fundet (går jeg ud fra). Jeg kan blot ikke få det til at virke. Når en bruger logger ind, skulle vedkommende gerne redirectes til sin tilladte jsp-side. Men i stedet bliver man i den aktuelle løsning ledt tilbage til login-siden igen og igen ?
Avatar billede arne_v Ekspert
06. juli 2010 - 00:41 #3
NetBeans eksemplet bruger container managed login.

Det er nok det nemmeste.

1) du putter reglerne i web.xml
2) du laver login.jsp og error.jsp
3) du putter bruger databasen i serverens konfiguration

og så virker det!

(jeg kan godt poste fungerende eksempler)

Hvis serveren er Tomcat, så kan du enten fjerne udkommenteringen af database bruger database eller fjerne udkommenteringen af XML bruger database.
Avatar billede kkaen Nybegynder
06. juli 2010 - 07:23 #4
Jeg er kommet i tanke om, hvad implementeringen for mange år siden gik ud på. Den var lavet i JAAS. Og så vidt jeg husker, så var den forholdsvis enkel og nem at implementere.
I min nuværende sag er det lidt overkill, hvis der bliver lavet SSL - altså brug Trusted Suplier. Men JAAS vil jeg rigtig gerne benytte som løsning.

Jeg tror faktisk, at det var dig Arne_V, som vejledte mig i min tidligere sag - så kan du ikke gøre det igen? :-)
Avatar billede kkaen Nybegynder
07. juli 2010 - 13:51 #5
Nu har jeg fundet lidt information omkring emnet på nettet, og har forsøgt at implementere det. Men det virker ikke helt (dog tæt på tror jeg).

Jeg har fulgt vejledningen her:
http://java.sun.com/j2se/1.5.0/docs/guide/security/jaas/tutorials/GeneralAcnAndAzn.html#SampleAzn

Og jeg har skrevet de efterfølgende kode-stumper. Men det virker som sagt ikke helt. Under kompileringen skrives der i outputtet: "WARNING: No Principals mapped to Role [student].
WARNING: No Principals mapped to Role [admin]."
Men jeg er ikke helt klar over, hvor man tildeler principals, hvis det ikke gøres manuelt i koden. Og jeg er ikke helt sikker på, hvordan det gøres korrekt i koden.
Hvad mangler jeg, eller gør jeg galt?

admin.policy:
grant codebase "./UploadedFiles/*",
        Principal sample.principal.SamplePrincipal "admin" {

  permission java.io.FilePermission "*", "read", "write";
};


Servlet som står for hele login ud fra tilsendte felter fra FORM (den endelige version skulle gerne hente credentials fra login på den enkelte computer - altså IKKE gennem en FORM):

package ServletPackage;

import java.io.IOException;
import java.io.PrintWriter;
import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.*;
import java.util.*;
import javax.servlet.*;
import javax.servlet.http.*;
import sun.net.www.http.HttpClient;
import java.security.*;
import javax.security.auth.*;
import javax.security.auth.login.LoginContext;
import javax.security.auth.login.LoginException;
import java.io.FilePermission;
import java.security.Policy;
import java.security.PrivilegedAction;
import java.util.ArrayList;
import java.util.List;
import javax.security.auth.Subject;
import javax.security.auth.callback.Callback;
import javax.security.auth.callback.CallbackHandler;
import javax.security.auth.callback.NameCallback;
import javax.security.auth.callback.PasswordCallback;

public class LoginAuthentication extends HttpServlet {
    private ServletConfig config;

    /**
    * Processes requests for both HTTP <code>GET</code> and <code>POST</code> methods.
    * @param request servlet request
    * @param response servlet response
    * @throws ServletException if a servlet-specific error occurs
    * @throws IOException if an I/O error occurs
    */
    protected void processRequest(HttpServletRequest request, HttpServletResponse response)
    throws ServletException, IOException {
        response.setContentType("text/html;charset=UTF-8");
        PrintWriter out = response.getWriter();
        try {
            final String studentName=new String("student");
            final String studentPassword=new String("student");
            final String adminName=new String("admin");
            final String adminPassword=new String("admin");

            if(studentName.equals(request.getParameter("user")) && studentPassword.equals(request.getParameter("pass")))
            {
                out.println("Vellykket login "+studentName);

                try{
                    LoginContext lc=new LoginContext("loginConext");
                    lc.login();
                }catch(Exception ex)
                {
                    System.out.println("LoginException: "+ex.toString());
                }

                Subject subject = Subject.getSubject(AccessController.getContext());
                System.out.println("\nSubject= "+subject+"\n");

                out.print("<form name=\"redirect\">\n");
                out.print("<center>\n");
                out.print("<font face=\"Arial\"><b>Du vil blive sendt videre i systemet om:<br><br>\n");
                out.print("<form>\n");
                out.print("<input type=\"text\" size=\"3\" name=\"redirect2\">\n");
                out.print("</form>\n");
                out.print("sekunder</b></font>\n");
                out.print("</center>\n");

                out.print("<script>\n");
                out.print("<!--\n");

                out.print("/*\n");
                out.print("Count down then redirect script\n");
                out.print("By JavaScript Kit (http://javascriptkit.com)\n");
                out.print("Over 400+ free scripts here!\n");
                out.print("*/\n");

                out.print("//change below target URL to your own\n");
                out.print("var targetURL=\"student/student.jsp\"\n");
                out.print("//change the second to start counting down from\n");
                out.print("var countdownfrom=3\n");

                out.print("var currentsecond=document.redirect.redirect2.value=countdownfrom+1\n");
                out.print("function countredirect(){\n");
                out.print("if (currentsecond!=1){\n");
                out.print("currentsecond-=1\n");
                out.print("document.redirect.redirect2.value=currentsecond\n");
                out.print("}\n");
                out.print("else{\n");
                out.print("window.location=targetURL\n");
                out.print("return\n");
                out.print("}\n");
                out.print("setTimeout(\"countredirect()\",1000)\n");
                out.print("}\n");

                out.print("countredirect()\n");
                out.print("//-->\n");
                out.print("</script>\n");

            }else if(adminName.equals(request.getParameter("user")) && adminPassword.equals(request.getParameter("pass")))
            {
                out.println("Vellykket login "+adminName);

                try
                {
                    LoginContext lc=new LoginContext("loginConext");
                    lc.login();

                    assignPrincipal(new RolePrincipal("admin"));
                    Policy defaultPolicy = Policy.getPolicy();
                    List policies = new ArrayList(1);
                    policies.add(defaultPolicy);

                    final File policyFile = new File("src/conf/admin.policy");
                    // Login a user
                    SimpleCallbackHandler cb = new SimpleCallbackHandler(adminName, adminPassword);
                    LoginContext ctx = new LoginContext("admin", cb);
                    ctx.login();
                    Subject subject = ctx.getSubject();
                    System.out.println("Logged in " + subject);
                    // Create privileged action block which limits permissions
                    // to only the Subject's permissions.
                    try
                    {
                        Subject.doAsPrivileged(subject, new PrivilegedAction() {
                            public Object run() {
                                policyFile.canRead();
                                System.out.println(adminName + " can access Policy file.");
                                return null;
                            }
                        }, null);
                    } catch (SecurityException e)
                    {
                        System.out.println("SecurityException: "+e.toString());
                    }
                    //assignPrincipal(new RolePrincipal("authenticateduser"));
                    Subject subject2 = Subject2.getSubject(AccessController.getContext());
                    System.out.println("\nSubject= "+subject2+"\n");
                }catch(Exception ex){
                    System.out.println("LoginException: "+ex.toString());
                }

                //countdown-example:
                out.print("<form name=\"redirect\">\n");
                out.print("<center>\n");
                out.print("<font face=\"Arial\"><b>Du vil blive sendt videre i systemet om:<br><br>\n");
                out.print("<form>\n");
                out.print("<input type=\"text\" size=\"3\" name=\"redirect2\">\n");
                out.print("</form>\n");
                out.print("sekunder</b></font>\n");
                out.print("</center>\n");

                out.print("<script>\n");
                out.print("<!--\n");

                out.print("/*\n");
                out.print("Count down then redirect script\n");
                out.print("By JavaScript Kit (http://javascriptkit.com)\n");
                out.print("Over 400+ free scripts here!\n");
                out.print("*/\n");

                out.print("//change below target URL to your own\n");
                out.print("var targetURL=\"admin/admin.jsp\"\n");
                out.print("//change the second to start counting down from\n");
                out.print("var countdownfrom=3\n");


                out.print("var currentsecond=document.redirect.redirect2.value=countdownfrom+1\n");
                out.print("function countredirect(){\n");
                out.print("if (currentsecond!=1){\n");
                out.print("currentsecond-=1\n");
                out.print("document.redirect.redirect2.value=currentsecond\n");
                out.print("}\n");
                out.print("else{\n");
                out.print("window.location=targetURL\n");
                out.print("return\n");
                out.print("}\n");
                out.print("setTimeout(\"countredirect()\",1000)\n");
                out.print("}\n");

                out.print("countredirect()\n");
                out.print("//-->\n");
                out.print("</script>\n");
            }else{
                out.println("Skriv et korrekt brugernavn og kodeord!\n");
                out.println("<a href='index.jsp'");
            }

            /* TODO output your page here
            out.println("<html>");
            out.println("<head>");
            out.println("<title>Servlet LoginAuthentication</title>"); 
            out.println("</head>");
            out.println("<body>");
            out.println("<h1>Servlet LoginAuthentication at " + request.getContextPath () + "</h1>");
            out.println("</body>");
            out.println("</html>");
            */
        } finally {
            out.close();
        }
    }

    @Override
    public void init(ServletConfig config) throws ServletException
    {
        this.config = config;
    }

    public class SimpleCallbackHandler implements CallbackHandler {
        private String name;
        private String password;
        public SimpleCallbackHandler(String name, String password) {
            this.name = name;
            this.password = password;
        }

        public void handle(Callback[] callbacks) {
            for (int i = 0; i < callbacks.length; i++)
            {
                Callback callback = callbacks[i];
                if (callback instanceof NameCallback)
                {
                    NameCallback nameCB = (NameCallback) callback;
                    nameCB.setName(name);
                }else if (callback instanceof PasswordCallback)
                {
                        PasswordCallback passwordCB = (PasswordCallback) callback;
                        passwordCB.setPassword(password.toCharArray());
                }
            }
        }
    }

    // <editor-fold defaultstate="collapsed" desc="HttpServlet methods. Click on the + sign on the left to edit the code.">
    /**
    * Handles the HTTP <code>GET</code> method.
    * @param request servlet request
    * @param response servlet response
    * @throws ServletException if a servlet-specific error occurs
    * @throws IOException if an I/O error occurs
    */
    @Override
    protected void doGet(HttpServletRequest request, HttpServletResponse response)
    throws ServletException, IOException {
        processRequest(request, response);
    }

    /**
    * Handles the HTTP <code>POST</code> method.
    * @param request servlet request
    * @param response servlet response
    * @throws ServletException if a servlet-specific error occurs
    * @throws IOException if an I/O error occurs
    */
    @Override
    protected void doPost(HttpServletRequest request, HttpServletResponse response)
    throws ServletException, IOException {
        processRequest(request, response);
    }

    /**
    * Returns a short description of the servlet.
    * @return a String containing servlet description
    */
    @Override
    public String getServletInfo() {
        return "Short description";
    }// </editor-fold>

}
Avatar billede kkaen Nybegynder
08. juli 2010 - 09:39 #6
Efter en del research indenfor emnet ser det ud til, at selve authentication er forholdsvis let at lave. Så den klarer jeg nok.

Problemet er nærmere authorization. Altså at sætte en form for stopper på biblioteker, som en pågældende bruger ikke har lov til at se, når man er logget ind. Reglerne herfor kan sættes op i en policy-file, men jeg er ikke helt med på, hvordan jeg nøjagtig får det til at virke. Og for at gøre mere kompliceret, så skal det jo gerne virke i TomCat. Så det er sådan set kun dét, mit spørgsmål her går på...?
Avatar billede kkaen Nybegynder
08. juli 2010 - 10:40 #7
Jeg har nu prøvet at mappe users til roles, som det står i:

http://www.chariotsolutions.com/geronimo/geronimo-1.1/security-application.html#example-role-mapping

Men uanset hvor jeg sætter data ind i web.xml, så kommer der fejl, og det indsatte er da heller ikke muligt ifølge intellisence...?
Avatar billede arne_v Ekspert
09. juli 2010 - 02:49 #8
Jeg tror at det er meget vigtigt at holde tingene skarp adskilt:
* validering af brugernavn/password <-> check af brugers adgang
* container managed <-> app managed

Det simpleste og formentligt fuldt tilstrækkelige er:
A) validering af brugernavn/password container managed
B) check af brugers adgang container managed

Det er det som jeg har beskrevet ovenfor.

#A kan laves med forskellige kilder:
- XML fil
- database
- JAAS

Mit forslag vil være at holde sig til XML fil indtil det virker, fordi det er langt det nemmeste.

Med hensyn til #B synes jeg at du skal starte med kun de helt simple regler i web.xml.
Avatar billede arne_v Ekspert
09. juli 2010 - 02:50 #9
Jeg kan poste et komplet eksempel.
Avatar billede arne_v Ekspert
09. juli 2010 - 02:56 #10
web.xml:

<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE web-app PUBLIC "-//Sun Microsystems, Inc.//DTD Web Application 2.3//EN" "http://java.sun.com/dtd/web-app_2_3.dtd">
<web-app>
  <security-constraint>
      <web-resource-collection>
          <web-resource-name>logintest open part</web-resource-name>
          <url-pattern>/open/*</url-pattern>
      </web-resource-collection>
      <auth-constraint>
          <role-name>user</role-name>
          <role-name>administrator</role-name>
      </auth-constraint>
  </security-constraint>
  <security-constraint>
      <web-resource-collection>
          <web-resource-name>logintest secure part</web-resource-name>
          <url-pattern>/secure/*</url-pattern>
      </web-resource-collection>
      <auth-constraint>
          <role-name>administrator</role-name>
      </auth-constraint>
  </security-constraint>
  <login-config>
      <auth-method>FORM</auth-method>
      <form-login-config>
          <form-login-page>/login.jsp</form-login-page>
          <form-error-page>/error.jsp</form-error-page>
      </form-login-config>
  </login-config>
  <security-role>
      <role-name>administrator</role-name>
      <role-name>user</role-name>
  </security-role>
</web-app>
Avatar billede arne_v Ekspert
09. juli 2010 - 02:56 #11
tomcat-users.xml:

<?xml version='1.0' encoding='utf-8'?>
<tomcat-users>
  <role rolename="administrator"/>
  <role rolename="user"/>
  <user username="userarne" password="x" roles="user"/>
  <user username="adminarne" password="x" roles="administrator,user"/>
</tomcat-users>
Avatar billede kkaen Nybegynder
09. juli 2010 - 09:13 #13
Men JAAS benytter sig da også af xml? Godt nok bliver brugernavn og kodeord typisk slået op i en database, men rettighederne angives da i en xml-fil? Og det er netop rettigheds-siden, der volder mig store problemer.

Men jeg har læst mig til, at når der benyttes <auth-method>FORM</auth-method>, så kommer der automatisk en login-form frem, når man prøver at tilgå ressourcer, som er beskyttet. Altså skal udvikleren ikke selv konstruere en login-form?
Avatar billede arne_v Ekspert
09. juli 2010 - 15:18 #14
Med hensyn til det sidste:

  <login-config>
      <auth-method>FORM</auth-method>
      <form-login-config>
          <form-login-page>/login.jsp</form-login-page>
          <form-error-page>/error.jsp</form-error-page>
      </form-login-config>
  </login-config>

saa angiver man hvilken login form der skal anvendes.
Avatar billede arne_v Ekspert
09. juli 2010 - 15:19 #15
login.jsp skal bruge nogle bestemte navne:

<form action="j_security_check" method="POST">
Username: <input type="text" name="j_username"><br>
Password: <input type="password" name="j_password"><br>
<input type="submit" value="Login">
</form>

for at virke sammen med Tomcat.
Avatar billede arne_v Ekspert
09. juli 2010 - 15:21 #16
Bemaerk at udover den nemme container managed beskyttelse baseret paa URL saa kan den kombineres med noget app managed beskyttelse.

Eksempel:

if(request.isUserInRole("adgangtilatgoerefoobar")) {
}
Avatar billede kkaen Nybegynder
10. juli 2010 - 19:26 #17
fre. d. 09. juli 2010 kl. 15:18:50| #14
Jeg mener blot, at jeg har set eksempler på, at der ved <auth-method>FORM</auth-method> ikke er angives noget i <form-login-page></form-login-page>-sektionen. Jeg gik derfor ud fra, at teknikken automatisk genererede en login-form, hvis der ikke angives sider til det?

fre. d. 09. juli 2010 kl. 15:21:12| #16
Jeg har tanker om, at implementere noget manuelt login, og så gemme resultatet i sessionen. For at styre adgang til bestemte sider, vil der på hver side være et check af data gemt i sessionen. Det er vel noget lignende koden skrevet i indlæget  fre. d. 09. juli 2010 kl. 15:21:12| #16 ? Eller er den omtalte løsning (altså mine tanker her) for "let" - altså så den ikke vil virke sim sikkerheds-funktion i praksis?
Avatar billede arne_v Ekspert
10. juli 2010 - 22:34 #18
Så vidt jeg kan se er form-login-page obligatorisk!

Og jeg er stensikker på at der ikke genereres en side, hvis den var valgfri, så ville der formentligt bare være et default navn.
Avatar billede arne_v Ekspert
10. juli 2010 - 22:36 #19
Det i #16 beskrevne er hvor brugeren logger ind i containeren, men hvor ikke alle adgangs checks laves i security constraints - nogen af adgangs checks laves i kode (JSP eller servlet).
Avatar billede arne_v Ekspert
10. juli 2010 - 22:38 #20
Det er absolut en mulighed at styre det hele både login og adgangs checks i app.

Det er lidt mere arbejde, men giver også lidt mere frihed.

Og teknikken er at få folk der ikke er logget ind redirected til en login side og ved successfuldt login sætte noget i session.
Avatar billede arne_v Ekspert
10. juli 2010 - 22:39 #21
Super banalt single page eksempel:

<%@page import="java.util.*"%>
<%
if((session == null) || (session.getAttribute("username") == null)) {
    String username = request.getParameter("username");
    String password = request.getParameter("password");
    if((username!=null)&&(password!=null)) {
        if((username.equals("arne")&&password.equals("arne"))||(username.equals("system")&&password.equals("system"))) {
            session.setAttribute("username", username);
            response.sendRedirect("secure.jsp");
            return;
        } else {
            %>
            Invalid username/password.
            <%
            return;
        }
    } else {
      %>
      <form action="secure.jsp" method="GET">
      Username: <input type="text" name="username"><br>
      Password: <input type="text" name="password"><br>
      <input type="submit" value="Login">
      </form>
      <%
      return;
    }
} else {
    if(session.getAttribute("username").equals("system")) {
        %>
        <strong>It works !!!!</strong>
        <%
        return;
    } else {
        %>
        No access.
        <%
        return;
    }
}
%>
Avatar billede arne_v Ekspert
10. juli 2010 - 22:44 #22
Og her et gammelt Struts 1 eksempel:


package test;

import java.io.*;

import javax.servlet.*;
import javax.servlet.http.*;

import org.apache.struts.action.*;

public class EnterAction extends Action {
    public ActionForward execute(ActionMapping mapping,
                                ActionForm form,
                                HttpServletRequest request,
                                HttpServletResponse response) throws IOException, ServletException {
        if(request.getSession().getAttribute("user") == null) {
            return mapping.findForward("not.logged.in");
        }
        return mapping.findForward("continue");
    }
}



package test;

import java.io.*;
import java.sql.*;

import javax.servlet.*;
import javax.servlet.http.*;

import org.apache.struts.action.*;

public class LoginAction extends Action {
    public ActionForward execute(ActionMapping mapping,
                                ActionForm form,
                                HttpServletRequest request,
                                HttpServletResponse response) throws IOException, ServletException {
        LoginForm lgifrm = (LoginForm)form;
        String username = lgifrm.getUsername();
        String password = lgifrm.getPassword();
        try {
            if(password.equals(StrutsUsers.getInstance().getPassword(username))) {
                request.getSession().setAttribute("user", lgifrm.getUsername());
                return mapping.findForward("login.ok");
            } else {
                ActionErrors errors = new ActionErrors();
                errors.add(ActionErrors.GLOBAL_ERROR, new ActionError("username.password.not.valid"));
                saveErrors(request, errors);
                return mapping.findForward("login.failure");
            }
        } catch (ClassNotFoundException ex) {
            ActionErrors errors = new ActionErrors();
            errors.add(ActionErrors.GLOBAL_ERROR, new ActionError("database.error"));
            saveErrors(request, errors);
            return mapping.findForward("login.failure");
        } catch (SQLException ex) {
            ActionErrors errors = new ActionErrors();
            errors.add(ActionErrors.GLOBAL_ERROR, new ActionError("database.error"));
            saveErrors(request, errors);
            return mapping.findForward("login.failure");
        }
    }
}



<%@ taglib uri="struts-html" prefix="html" %>
<html>
<head>
<title>Login</title>
</head>
<body>
<h1>Login</h1>
<html:errors/>
<html:form action="/Login">
Username: <html:text property="username"/>
<br/>
Password:
<html:password property="password"/>
<br/>
<html:submit/><html:reset/>
</html:form>
</body>
</html>



<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE struts-config PUBLIC "-//Apache Software Foundation//DTD Struts Configuration 1.1//EN" "http://jakarta.apache.org/struts/dtds/struts-config_1_1.dtd" >
<struts-config>
    <form-beans>
        <form-bean name="loginForm" type="test.LoginForm"/>
        <form-bean name="addForm" type="test.AddForm"/>
    </form-beans>
    <action-mappings>
        <action path="/Start" type="test.StartAction">
            <forward name="logged.in" path="/start.jsp"/>
            <forward name="not.logged.in" path="/login.jsp"/>
        </action>
        <action path="/Login" type="test.LoginAction" name="loginForm" input="/login.jsp">
            <forward name="login.ok" path="/start.jsp"/>
            <forward name="login.failure" path="/login.jsp"/>
        </action>
        <action path="/List" type="test.ListAction">
            <forward name="not.logged.in" path="/login.jsp"/>
            <forward name="data.ok" path="/list.jsp"/>
            <forward name="data.error" path="/error.jsp"/>
        </action>
        <action path="/Enter" type="test.EnterAction">
            <forward name="not.logged.in" path="/login.jsp"/>
            <forward name="continue" path="/add.jsp"/>
        </action>
        <action path="/Add" type="test.AddAction" name="addForm" input="/add.jsp">
            <forward name="not.logged.in" path="/login.jsp"/>
            <forward name="data.ok" path="/add.jsp"/>
            <forward name="data.error" path="/error.jsp"/>
        </action>
    </action-mappings>
    <message-resources parameter="application" null="false"/>
</struts-config>


Hvis du ikke kender Struts, så forklarer det nok ikke så meget.
Avatar billede kkaen Nybegynder
11. juli 2010 - 12:56 #23
Struts siger mig desværre intet :-(

Jeg mener bare, jeg har læst mig til, at sessioner kan hackes. Men da f.eks. JAAS benytter sig af sessioner, gik jeg ud fra, at den aktuelle teknologi benyttede sig af noget ret avanceret sikkerheds-halløj, til at sikre sig mod hacks. Og i den sammenhæng gik jeg ud fra, at man ikke individuelt bare lige kan strikke noget lignende sammen rent sikkerhedsmæssigt?

PS:
lør. d. 10. juli 2010 kl. 22:39:38| #21
er der en specifik grund til, at alle sektionerne afsluttes med return;, eller er det blot god kode-skik?
Avatar billede arne_v Ekspert
11. juli 2010 - 17:13 #24
Alle web løsninger: Java, ASP.NET, PHP, Ror etc, bruger sessions.

Det er klart at ved at bruge noget indbygget i serveren undgår man at lave dumme fejl selv.

Men serveren kan ikek lave noget som man ikke selv kan lave.
Avatar billede arne_v Ekspert
11. juli 2010 - 17:13 #25
#21

Er ret langt fra god kode skik.

:-)

Jeg tror bare at return er der for at være sikker på at der ikke vises noget længere nede.
Avatar billede kkaen Nybegynder
11. juli 2010 - 17:22 #26
#24
Naturligvis. Men det, jeg forsøgte at sige, var, at når der nu er udviklet en omfattende teknologi (JAAS), så er det nok ikke muligt for en lille programmør som mig, at lave noget tilsvarende sådan lige vupti.
Men det har vel ikke noget med serveren at gøre (altså spørgsmålet her mht. sessioner). Hverken fysisk eller software-mæssigt.
Avatar billede arne_v Ekspert
13. juli 2010 - 04:06 #27
JAAS er et framework / en standard for hvordan to stykker Java software kan udveksle sikkerhedsoplysninger.

Du kan bruge JAAS hvis du skal have Tomcat integreret med en ekeisterende brugerdatabase du har i et andet format end hvad Tomcat understøtter.

Men jeg mener ikke rigtigt at det løser nogle af dine problemer.
Avatar billede kkaen Nybegynder
13. juli 2010 - 08:54 #28
Det hele står og falder med <security-constraint> i web.xml. Så det må jeg prøve at implementere nogle forsøg på. Men det kan først blive om en 2-3 uger...
Avatar billede arne_v Ekspert
13. juli 2010 - 18:21 #29
Som vist i #16 kan du godt kombinere container managed login med noget app managed access check.
Avatar billede arne_v Ekspert
25. juli 2010 - 22:44 #30
all set?
Avatar billede kkaen Nybegynder
17. august 2010 - 09:25 #31
Nu har jeg endelig fået set på det.
Jeg har lavet noget app-managed-check, da jeg først skulle foretage nogle forsøg med TomCat. Men nu har jeg implementeret TomCat-løsningen, og det virker. Dog skal det siges, at jeg har testet det nu, og de første forsøg opførte sig som forventet. Men nu har jeg lige prøvet at tilgå den mindst restriktive del af applikationen igen (altså login som "bruger"), og nu giver det en exception 500. Det er en null-pointer, og så står der en reference ned til brugerens jsp-side. SÅ det må jeg lige se på, selvom der da ikke burde være referencer ned til en jsp-sides indhold, når der i TomCat foretages check på typen af login (?).

Men hvis vi nu antager, at jeg får løst dette problem, så har jeg et tillægs-spørgsmål. I applikationen har jeg nemlig en mappe ude i roden, hvor admin har både læse- og skrive-rettigheder, men en bruger må KUN have læse-rettigheder. HVordan angives dette i TomCat? Kan man også angive noget read/write i web.xml?
Avatar billede kkaen Nybegynder
17. august 2010 - 10:47 #32
Hmm, føromtalte exception 500 peger på en linie i jsp-siden, hvor en variabel i sessionen blot sætte stil null. Så fejlmeldingen får jeg ikke meget ud af. Mon det er et andet sted i systemet, hvor den er opstået? Ja, det er det jo nok. Men er det så ikke et tegn på, at opsætningen af TomCat ikke virker korrekt?
Avatar billede kkaen Nybegynder
17. august 2010 - 15:20 #33
Nu har jeg erfaret, at TomCat kan installeres til Xampp som add-on. Og herigennem kan man så benytte noget administration-noget, som vist giver meget bedre grafisk overblik over, hvad man egentlig laver. Jeg har også læst, at det frarådes, at man manuelt sætter <context> m.m. ind i tomcat's administrations-filer. Så jeg ser lige på den førnævnte administrations-del i morgen.
Avatar billede arne_v Ekspert
17. august 2010 - 21:29 #34
Admin RW & user R ville jeg loese som:
- container check som tillader R
- app checker om W er admin
Avatar billede arne_v Ekspert
17. august 2010 - 21:30 #35
Der er et par muligheder for at definere context udenfor server.xml, hvillket er lidt mindre intrusive.
Avatar billede kkaen Nybegynder
18. august 2010 - 09:09 #36
Jeg gik egentlig ud fra, at forskellen på container-/app-managed var, om indstillingerne var angivet i web.xml eller om selve koden i applikationen tog vare på det. Men jeg har på fornemmelsen, at dette ikke er tilfældet?
Avatar billede kkaen Nybegynder
18. august 2010 - 09:19 #37
Helt konkret så har jeg et bibliotek med filer i. Indholdet af dette bibliotek må brugere KUN se, mens administratorer både må se og skrive/overskrive.
Disse rettigheder kan jeg ikke angive i servlet-kode eller lignende, da en bruger blot kan gå udenom servletten, hvis vedkommende kender den absolute url til ressourcen. Altså skal TomCat stå for den sikkerhed. Og hvordan vil du helt nøjagtig implementere et konkret eksempel herpå?
Avatar billede arne_v Ekspert
18. august 2010 - 09:44 #38
Jo - det er rigtigt forstaaet.
Avatar billede arne_v Ekspert
18. august 2010 - 09:45 #39
Hvis det er adgang til filer i et dir, saa skal du saette det op saaledes at de ikke kan tilgoes direkte, men skal gennem noget Java kode som kan checke adgang.
Avatar billede kkaen Nybegynder
18. august 2010 - 11:35 #40
Det er med adgangen til de filer, det kniber med. Jeg har angivet biblioteket i web.xml, og angivet rolle-navne, men jeg kan opnå tilgang til filerne, selvom jeg ikke er logget ind - ikke engang logged ind som noget "forkert"...?
Avatar billede arne_v Ekspert
18. august 2010 - 22:48 #41
Bliver de servet af Tomcat?
Avatar billede kkaen Nybegynder
19. august 2010 - 13:32 #42
Det er tomcat, som står for det, ja.
Men jeg har ladet mig fortælle, at selvom tomcat giver adgang til ressourcerne (når brugeren ser adressen til det i adresse-feltet i browseren eller selv regner den ud ved f.eks. at se på koden), så sørger tomcat også for, at en bruger ikke har skriveadgang til ressourcerne. Derved kan ressourcerne ikke overskrives. Det er jo altid noget, men brugeren har jo stadig adgang til ressourcerne gennem addresse-feltet i browseren, hvilket ikke altid er godt. I dette tilfælde gør det ikke så meget, men det kunne det da nemt gøre.
Avatar billede kkaen Nybegynder
21. september 2010 - 16:25 #43
Skulle vi få lukket dette spørgsmål, Arne_V ?
Avatar billede arne_v Ekspert
21. september 2010 - 20:33 #44
Hvis du placerer ting udenfor det servede trae og bruger Java kode til al adgang, saa kan man jo helt styre det som man vil

Jeg smed allerede et svar for et par maaneder siden.
Avatar billede kkaen Nybegynder
21. september 2010 - 21:07 #45
Ja, det gjorde du. Jeg gik ud fra, at det fremgik ved bunden af tråden :-)
Avatar billede Ny bruger Nybegynder

Din løsning...

Tilladte BB-code-tags: [b]fed[/b] [i]kursiv[/i] [u]understreget[/u] Web- og emailadresser omdannes automatisk til links. Der sættes "nofollow" på alle links.

Loading billede Opret Preview
Kategori
Kurser inden for grundlæggende programmering

Log ind eller opret profil

Hov!

For at kunne deltage på Computerworld Eksperten skal du være logget ind.

Det er heldigvis nemt at oprette en bruger: Det tager to minutter og du kan vælge at bruge enten e-mail, Facebook eller Google som login.

Du kan også logge ind via nedenstående tjenester