2

屋外で wbesciptr を実行すると問題が発生します。何が起こっているのかわかりませんが、Java で書かれた Web スクリプトを実行するたびに 401 エラー コードが表示されます。私はjavascriptで同様のウェブスクリプトを持っていますが、問題なく動作します。

アドレス: http://localhost:8080/proxy/alfresco/api/repository/person/my-captcha?type=validate&token=MILUR1445505693188&word=EWGVNB

エラーログ:

2015-10-23 09:32:35,030 INFO [web.site.EditionInterceptor] [http-bio-8080-exec-7] Alfresco からライセンス情報を取得できません: 401

xml の私の Bean:

<bean id="webscript.pl.[...].ca.guest.my-captcha.get"
    class="pl.[...].repo.web.scripts.ca.MyCaptcha" 
    parent="webscript">
</bean>

xml のプロパティ:

<webscript>
    <shortname>My captcha</shortname>
    <description>Get captcha</description>
    <url>/api/ca/guest/my-captcha</url>
    <format default="json"/>
    <family>[...]</family>
    <authentication runas="admin">none</authentication>
</webscript>

総括:

{
    "token": <#if token?exists>"${token}"<#else>null</#if>,
    "response": <#if response?exists>"${response}"<#else>null</#if>,
    "image": <#if image?exists>"${image}"<#else>null</#if>
}

および Java クラス:

public class MyCaptcha extends DeclarativeWebScript {

    private static final Logger LOGGER = Logger.getLogger(MyCaptcha.class);
    private static final String CAPTCHA_VALIDATE = "validate";
    private static final String CAPTCHA_CREATE = "create";
    private static final String PARAMETER_TYPE = "type";
    private static final String PARAMETER_TOKEN = "token";
    private static final String PARAMETER_WORD = "word";
    private static final String PARAMETER_IMAGE = "image";
    private static final String PARAMETER_RESPONSE = "response";
    private static Map<String, String> TOKENCACHE = new HashMap<>();

    @Override
    protected Map<String, Object> executeImpl(WebScriptRequest req,
            Status status, Cache cache) {
        Map<String, Object> result;
        String request = req.getParameter(PARAMETER_TYPE);
        if (request != null && request.equals(CAPTCHA_CREATE)) {
            result = createCaptcha();
            return result;
        } else if (request != null && request.equals(CAPTCHA_VALIDATE)) {
            String token = req.getParameter(PARAMETER_TOKEN);
            String word = req.getParameter(PARAMETER_WORD);
            result = new HashMap<>();
            result.put(PARAMETER_RESPONSE, token != null && word != null
                    && TOKENCACHE.get(token).equalsIgnoreCase(word)
                    ? "true"
                    : "false");
            return result;
        } else {
            result = new HashMap<>();
            result.put(PARAMETER_RESPONSE, "false");
            return result;
        }
    }

    public Map<String, Object> createCaptcha() {
        int width = 150;
        int height = 50;
        BufferedImage bufferedImage = new BufferedImage(150, 50,
                BufferedImage.TYPE_INT_RGB);
        Graphics2D g2d = bufferedImage.createGraphics();
        g2d.setFont(new Font("Georgia", Font.BOLD, 18));

        RenderingHints renderingHints = new RenderingHints(
                RenderingHints.KEY_ANTIALIASING,
                RenderingHints.VALUE_ANTIALIAS_ON);

        renderingHints.put(RenderingHints.KEY_RENDERING,
                RenderingHints.VALUE_RENDER_QUALITY);

        g2d.setRenderingHints(renderingHints);

        // drawing gradient
        GradientPaint gp = new GradientPaint(0, 0, Color.lightGray, 0,
                height / 1, Color.white, true);

        g2d.setPaint(gp);
        g2d.fillRect(0, 0, width, height);

        // setting font's color
        g2d.setColor(new Color(0, 0, 0));

        // creating chain of random letters
        char captchaWord[] = new char[6];
        String captcha = "";
        Random r = new Random();
        for (int i = 0; i < 6; i++) {
            captchaWord[i] = (char) (65 + Math.abs(r.nextInt()) % 24);
            captcha += captchaWord[i];
        }

        // drawing chain of random letters on image
        int x = 0;
        for (int i = 0; i < captchaWord.length; i++) {
            x += 10 + (Math.abs(r.nextInt()) % 15);
            g2d.drawChars(captchaWord, i, 1, x + 5,
                    20 + Math.abs(r.nextInt()) % 20);
        }

        ByteArrayOutputStream baos = new ByteArrayOutputStream();
        // OutputStream b64 = new Base64.OutputStream(baos);
        Map<String, Object> result = new HashMap<>();
        try {
            ImageIO.write(bufferedImage, "png", baos);
            byte[] bytes = baos.toByteArray();
            String base64bytes = Base64.encodeBytes(bytes);
            String src = "data:image/png;base64," + base64bytes;
            String token = createToken(captcha);
            result.put(PARAMETER_IMAGE, src); // b64.toString("UTF-8"));
            result.put(PARAMETER_TOKEN, token);
            TOKENCACHE.put(token, captcha);
            return result;
        } catch (IOException e) {
            LOGGER.error("Exception : can't write image into base64 ::", e);
            // ? e.printStackTrace();
            result.put("error", "can't write image into base64");
            return result;
        }
    }

    // this function creates unique (hope so) token to recognize captcha
    public String createToken(String captcha) {
        StringBuffer token = new StringBuffer();
        Date date = new Date();
        Random r = new Random();
        token.append((char) (65 + Math.abs(r.nextInt()) % 24))
                .append((char) (65 + Math.abs(r.nextInt()) % 24))
                .append((char) (65 + Math.abs(r.nextInt()) % 24))
                .append((char) (65 + Math.abs(r.nextInt()) % 24))
                .append((char) (65 + Math.abs(r.nextInt()) % 24))
                .append(date.getTime());
        return token.toString();
    }
}
4

1 に答える 1

1

解決しました(幸い)。アドレスに問題がありました。one/service/.../my-captcha に直接接続するのではなく、プロキシを使用してウェブスクリプトを呼び出していました

于 2015-10-23T07:43:13.967 に答える