Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(28)

Unified Diff: chrome/android/java/src/org/chromium/chrome/browser/CertificateViewer.java

Issue 12045081: Android implementation of WebsiteSettingsUi (Closed) Base URL: svn://svn.chromium.org/chrome/trunk/src
Patch Set: fix memory leak Created 7 years, 11 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View side-by-side diff with in-line comments
Download patch
Index: chrome/android/java/src/org/chromium/chrome/browser/CertificateViewer.java
diff --git a/chrome/android/java/src/org/chromium/chrome/browser/CertificateViewer.java b/chrome/android/java/src/org/chromium/chrome/browser/CertificateViewer.java
new file mode 100644
index 0000000000000000000000000000000000000000..bfcf3e2b2d94b0b465fae2f6be37f5a2dcc2292e
--- /dev/null
+++ b/chrome/android/java/src/org/chromium/chrome/browser/CertificateViewer.java
@@ -0,0 +1,201 @@
+// Copyright (c) 2013 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+package org.chromium.chrome.browser;
+
+import android.app.Dialog;
+import android.content.Context;
+import android.graphics.Typeface;
+import android.net.http.SslCertificate;
+import android.text.format.DateFormat;
+import android.util.Log;
+import android.view.View;
+import android.widget.AdapterView;
+import android.widget.AdapterView.OnItemSelectedListener;
+import android.widget.ArrayAdapter;
+import android.widget.LinearLayout;
+import android.widget.ScrollView;
+import android.widget.Spinner;
+import android.widget.TextView;
+
+import org.chromium.chrome.R;
+
+import java.io.ByteArrayInputStream;
+import java.security.cert.Certificate;
+import java.security.cert.CertificateException;
+import java.security.cert.CertificateFactory;
+import java.security.cert.X509Certificate;
+import java.util.ArrayList;
+
+/**
+ * UI component for displaying certificate information.
+ */
+public class CertificateViewer implements OnItemSelectedListener {
+ CertificateFactory mCertificateFactory;
Ted C 2013/01/25 02:04:05 are these intentionally package scoped? I suspect
Yaron 2013/01/25 19:25:17 Done.
+ Context mContext;
+ ArrayList<LinearLayout> mViews;
+ ArrayList<String> mTitles;
+ int mPadding;
+
+ public static void showCert(Context context, byte[] der_data) {
Ted C 2013/01/25 02:04:05 all public methods should have javadoc.
Yaron 2013/01/25 19:25:17 Done.
+ CertificateViewer viewer = new CertificateViewer(context);
+ viewer.showCertificate(der_data);
+ }
+
+ public static void showCertChain(Context context, byte[][] der_data) {
Ted C 2013/01/25 02:04:05 der_data should be camel cased (and all other usag
Yaron 2013/01/25 19:25:17 Done.
+ CertificateViewer viewer = new CertificateViewer(context);
+ viewer.showCertificateChain(der_data);
+ }
+
+ private CertificateViewer(Context context) {
+ mContext = context;
+ mViews = new ArrayList<LinearLayout>();
+ mTitles = new ArrayList<String>();
+ mPadding = (int) context.getResources().getDimension(
+ R.dimen.certificate_viewer_padding) / 2;
Ted C 2013/01/25 02:04:05 why is it dividing by two?
Yaron 2013/01/25 19:25:17 I tried removing and there's too much vertical spa
+ }
+
+ // Show information about DER-encoded data representing an X509 certificate.
+ private void showCertificate(byte[] der_data) {
+ addCert(der_data);
+ showDialogForView(mViews.get(0));
+ }
+
+ // Show information about an array of DER-encoded data representing a X509 certificate chain.
+ // A spinner will be displayed allowing the user to select which certificate to display.
+ private void showCertificateChain(byte[][] der_data) {
+ for (int i = 0; i < der_data.length; ++i) {
Ted C 2013/01/25 02:04:05 i++ in java land (applicable other places in this
Yaron 2013/01/25 19:25:17 Done.
+ addCert(der_data[i]);
+ }
+ ArrayAdapter<String> arrayAdapter = new ArrayAdapter<String>(mContext,
+ android.R.layout.simple_spinner_item,
+ mTitles);
+ arrayAdapter.setDropDownViewResource(android.R.layout.simple_spinner_dropdown_item);
+
+ Spinner spinner = new Spinner(mContext);
+ spinner.setAdapter(arrayAdapter);
+ spinner.setOnItemSelectedListener(this);
+
+ LinearLayout container = new LinearLayout(mContext);
+ container.setOrientation(LinearLayout.VERTICAL);
+ container.addView(spinner);
+
+ for (int i = 0; i < mViews.size(); ++i) {
+ LinearLayout certificateView = mViews.get(i);
+ if (i != 0) {
+ certificateView.setVisibility(LinearLayout.GONE);
+ }
+ container.addView(certificateView);
+ }
+
+ showDialogForView(container);
+ }
+
+ // Displays a dialog with scrolling for the given view.
+ private void showDialogForView(View view) {
+ Dialog dialog = new Dialog(mContext);
+ dialog.setTitle(R.string.certtitle);
+ ScrollView scrollView = new ScrollView(mContext);
+ scrollView.addView(view);
+ dialog.addContentView(scrollView,
+ new LinearLayout.LayoutParams(LinearLayout.LayoutParams.MATCH_PARENT,
+ LinearLayout.LayoutParams.MATCH_PARENT));
Ted C 2013/01/25 02:04:05 should be indented 8 from the start of the line.
Yaron 2013/01/25 19:25:17 Done.
+ dialog.show();
+ }
+
+ private void addCert(byte[] der_data) {
+ try {
+ if (mCertificateFactory == null) {
+ mCertificateFactory = CertificateFactory.getInstance("X.509");
Ted C 2013/01/25 02:04:05 should X.509 be a constant?
Yaron 2013/01/25 19:25:17 Done.
+ }
+ Certificate cert = mCertificateFactory.generateCertificate(
+ new ByteArrayInputStream(der_data));
+ addCertDetails(cert);
+ } catch (CertificateException e) {
+ Log.e("CertViewer", "Error parsing certificate" + e.toString());
+ }
+ }
+
+ private void addCertDetails(Certificate cert) {
+ LinearLayout certificateView = new LinearLayout(mContext);
+ mViews.add(certificateView);
+ certificateView.setOrientation(LinearLayout.VERTICAL);
+
+ X509Certificate x509 = (X509Certificate)cert;
Ted C 2013/01/25 02:04:05 space between the cast and the variable.
Yaron 2013/01/25 19:25:17 Done.
+ SslCertificate sslCert = new SslCertificate(x509);
+
+ mTitles.add(sslCert.getIssuedTo().getCName());
+
+ addSectionTitle(certificateView, R.string.certissuedto);
+ addItem(certificateView, R.string.certcn, sslCert.getIssuedTo().getCName());
+ addItem(certificateView, R.string.certo, sslCert.getIssuedTo().getOName());
+ addItem(certificateView, R.string.certou, sslCert.getIssuedTo().getUName());
+ addItem(certificateView, R.string.certsn,
+ formatSerial(x509.getSerialNumber().toByteArray()));
+
+ addSectionTitle(certificateView, R.string.certissuedby);
+ addItem(certificateView, R.string.certcn, sslCert.getIssuedBy().getCName());
+ addItem(certificateView, R.string.certo, sslCert.getIssuedBy().getOName());
+ addItem(certificateView, R.string.certou, sslCert.getIssuedBy().getUName());
+
+ addSectionTitle(certificateView, R.string.certvalidity);
+ java.text.DateFormat dateFormat = DateFormat.getDateFormat(mContext);
+ addItem(certificateView, R.string.certissuedon,
+ dateFormat.format(sslCert.getValidNotBeforeDate()));
+ addItem(certificateView, R.string.certexpireson,
+ dateFormat.format(sslCert.getValidNotAfterDate()));
+ }
+
+ private void addSectionTitle(LinearLayout certificateView, int label) {
+ TextView title = addLabel(certificateView, label);
+ title.setAllCaps(true);
+ }
+
+ private void addItem(LinearLayout certificateView, int label, String value) {
+ if (!value.isEmpty()) {
Ted C 2013/01/25 02:04:05 I would probably do if (value.isEmpty()) return;
Yaron 2013/01/25 19:25:17 Done.
+ addLabel(certificateView, label);
+ addValue(certificateView, value);
+ }
+ }
+
+ private TextView addLabel(LinearLayout certificateView, int label) {
+ TextView t = new TextView(mContext);
+ t.setPadding(mPadding, mPadding / 2, mPadding, 0);
+ t.setText(label);
+ t.setTypeface(Typeface.defaultFromStyle(Typeface.BOLD));
+ certificateView.addView(t);
+ return t;
+ }
+
+ private void addValue(LinearLayout certificateView, String value) {
+ TextView t = new TextView(mContext);
+ t.setText(value);
+ t.setPadding(mPadding, 0, mPadding, mPadding / 2);
+ certificateView.addView(t);
+ }
+
+ static private String formatSerial(byte[] bytes) {
Ted C 2013/01/25 02:04:05 private before static.
Yaron 2013/01/25 19:25:17 Done.
+ StringBuilder sb = new StringBuilder();
+ for (int i = 0; i < bytes.length; i++) {
+ sb.append(String.format("%02X", bytes[i]));
+ if (i != bytes.length - 1) {
+ sb.append(':');
+ }
+ }
+ return sb.toString();
+ }
+
+ @Override
+ public void onItemSelected(AdapterView<?> parent, View view, int position, long id) {
+ for (int i = 0; i < mViews.size(); ++i) {
+ mViews.get(i).setVisibility(
+ i == position ? LinearLayout.VISIBLE : LinearLayout.GONE);
+ }
+
+ }
+
+ @Override
+ public void onNothingSelected(AdapterView<?> parent) {
+ }
+}

Powered by Google App Engine
This is Rietveld 408576698