您的位置:首页 > 产品设计 > UI/UE

使用TrueLicense来保护我们的JAVA软件产品

2006-01-02 00:58 1351 查看

使用TrueLicense来保护我们的JAVA软件产品

也可以查看我的wiki:http://sms.i6688.com/pages/viewpage.action?pageId=25
我们的JAVA软件产品有时需要限制非法用户,只有购买了LICENSE的用户才能使用,因此,我们可以通过TrueLicense来实现。
首先要用KeyTool工具来生成私匙库:
keytool -genkey -alias privatekey -keystore privateKeys.store
然后把私匙库内的公匙导出到一个文件当中:
keytool -export -alias privatekey -file certfile.cer -keystore privateKeys.store
然后再把这个证书文件导入到公匙库:
keytool -import -alias publiccert -file certfile.cer -keystore publicCerts.store

服务器端利用私匙库来创建license的代码例子:

package com.sourceware.license;

import de.schlichtherle.license.*;
import java.io.*;
import java.util.*;
import javax.security.auth.x500.X500Principal;
import java.util.prefs.Preferences;

/**
* <p>Title: CMVP通用媒体增值业务平台</p>
*
* <p>Description: CMVP通用媒体增值业务平台</p>
*
* <p>Copyright: Copyright (c) 2005</p>
*
* <p>Company: source-ware.com inc.</p>
*
* @author 黑山
* @version 2.0
*/
public class SWLicenseManager {
public SWLicenseManager() {
}

LicenseContent verifyLicenseKey(LicenseParam parameter) {
// Create a configured license manager.
LicenseManager manager = new LicenseManager(parameter);
try {
// Verify the previously installed current license certificate.
return manager.verify();
}
catch (Exception exc) {
System.err.println("Could not verify license key");
exc.printStackTrace();
return null;
}
}

void installLicenseKey(LicenseParam parameter, File keyFile) {
// Create a configured license manager.
LicenseManager manager = new LicenseManager(parameter);
try {
// Load the license key, verify and install it as the current license key.
manager.install(keyFile);
}
catch (Exception exc) {
System.err.println("Could not install license certificate");
exc.printStackTrace();
}
}

void createLicenseKey(LicenseParam parameter, LicenseContent content) {
// Create a configured license manager.
LicenseManager manager = new LicenseManager(parameter);
try {
// Create the license key from the license content and save it to a file.
manager.store(content, new File("license.lic"));
}
catch (Exception exc) {
System.err.println("Could not save license key");
exc.printStackTrace();
}
}

//
// Customizable global properties.
//

/** The product id of your software */
public static final String PRODUCT_ID = "cmvp20"; // CUSTOMIZE

/**
* The subject for the license manager and also the alias of the private
* key entry in the keystore.
*/
public static final String SUBJECT = "别名"; // CUSTOMIZE

/** The resource name of your private keystore file. */
public static final String KEYSTORE_RESOURCE = "私匙库文件名"; // CUSTOMIZE

/** The password for the keystore. */
public static final String KEYSTORE_STORE_PWD = "私匙库密码"; // CUSTOMIZE

/* The password for the private key entry in the keystore. */
public static final String KEYSTORE_KEY_PWD = "私匙库主键密码"; // CUSTOMIZE

/** The password to encrypt the generated license key file. */
public static final String CIPHER_KEY_PWD = "即将生成的license密码"; // CUSTOMIZE

/**
* The filename to be displayed for the generated binary key file when
* delivered. Please note that this is not used to write to a file of
* this name.
*/
public static final String DISPLAY_FILENAME = "license.lic"; // CUSTOMIZE

//
// The rest of this key generator does not need to get customized.
//

/** The MIME type of the generated binary key file. */
public static final String MIME_TYPE = "application/octet-stream";

//
// Possible key generator exit codes
//

/**
* Return <code>ERC_SUCCESS</code> on succesful creation of a textual key.
* Note that this example creates a binary key and thus this constant is not
* used here
*/
//public static final int ERC_SUCCESS = 00;

/**
* Return <code>ERC_SUCCESS_BIN</code> on succesful creation of a binary
* key. (Which could contain text as well, if the content type is specified
* as <code>text/plain</code>)
*/
public static final int ERC_SUCCESS_BIN = 01;

/**
* Return <code>ERC_ERROR</code> for general errors.
*/
public static final int ERC_ERROR = 10;

/**
* Return <code>ERC_MEMORY</code> if memory allocation fails.
*/
public static final int ERC_MEMORY = 11;

/**
* Return <code>ERC_FILE_IO</code> on IOException
*/
public static final int ERC_FILE_IO = 12;

/**
* Return <code>ERC_BAD_ARGS</code> if the command line parameters are
* bad.
*/
public static final int ERC_BAD_ARGS = 13;

/**
* Return <code>ERC_BAD_INPUT</code> if a particular input value is
* missing or has a bad value. Don't forget to supply a meaningful error
* message naming the exact cause of the error.
*/
public static final int ERC_BAD_INPUT = 14;

/**
* Return <code>ERC_EXPIRED</code> if this generator is expired. This can
* be used to limit the lifetime of this generator.
*/
//public static final int ERC_EXPIRED = 15;

/**
* Return <code>ERC_INTERNAL</code> if an unhandled exception occurs.
*
* @see java.lang.Exception
*/
//public static final int ERC_INTERNAL = 16;

/** Encoding keys in properties. */
public static final String ENCODING_KEY = "ENCODING";
public static final String PRODUCT_ID_KEY = "PRODUCT_ID";
public static final String PURCHASE_ID_KEY = "PURCHASE_ID";
public static final String RUNNING_NO_KEY = "RUNNING_NO";
public static final String PURCHASE_DATE_KEY = "PURCHASE_DATE";
public static final String LANGUAGE_ID_KEY = "LANGUAGE_ID";
public static final String QUANTITY_KEY = "QUANTITY";
public static final String REG_NAME_KEY = "REG_NAME";
public static final String ADDITIONAL1_KEY = "ADDITIONAL1";
public static final String ADDITIONAL2_KEY = "ADDITIONAL2";
public static final String RESELLER_KEY = "RESELLER";
public static final String LASTNAME_KEY = "LASTNAME";
public static final String FIRSTNAME_KEY = "FIRSTNAME";
public static final String COMPANY_KEY = "COMPANY";
public static final String EMAIL_KEY = "EMAIL";
public static final String PHONE_KEY = "PHONE";
public static final String FAX_KEY = "FAX";
public static final String STREET_KEY = "STREET";
public static final String ZIP_KEY = "ZIP";
public static final String CITY_KEY = "CITY";
public static final String STATE_KEY = "STATE";
public static final String COUNTRY_KEY = "COUNTRY";

/** Default encoding for properties. */
public static final String ENCODING_PROPERTIES = "ISO-8859-1";

/** Default share-it encoding if key not present in properties. */
public static final String ENCODING_DEFAULT = ENCODING_PROPERTIES;

protected static final LicenseManager manager = new LicenseManager(
new DefaultLicenseParam(
SUBJECT,
Preferences.userRoot(),
new DefaultKeyStoreParam(
SWLicenseManager.class, // CUSTOMIZE
KEYSTORE_RESOURCE,
SUBJECT,
KEYSTORE_STORE_PWD,
KEYSTORE_KEY_PWD),
new DefaultCipherParam(CIPHER_KEY_PWD)));

/**
* Validates the properties and generates a license certificate file.
*/
private static void generateLicense(Properties props, File certFile) throws
Exception {
// Check for supported product id.
final String productId = props.getProperty(PRODUCT_ID_KEY);
if (!PRODUCT_ID.equals(productId)) {
throw new BadInputException("Bad product ID: " + productId);
}

final StringBuffer dn = new StringBuffer();
addAttribute(dn, "CN", props.getProperty(FIRSTNAME_KEY)
+ ' ' + props.getProperty(LASTNAME_KEY));
if (dn.length() == 0) {
addAttribute(dn, "CN", props, REG_NAME_KEY);
}
addAttribute(dn, "O", props, COMPANY_KEY);
addAttribute(dn, "STREET", props, STREET_KEY);
addAttribute(dn, "L", props.getProperty(ZIP_KEY)
+ ' ' + props.getProperty(CITY_KEY));
addAttribute(dn, "ST", props, STATE_KEY);
addAttribute(dn, "C", props, COUNTRY_KEY);
final X500Principal holder = new X500Principal(dn.toString());
final X500Principal issuer = new X500Principal(
"OU=share-it!,O=element 5 AG,STREET=Vogelsanger Strasse 78,L=50823 K/u00F6ln,ST=Nordrhein-Westfalen,C=DE");

final LicenseContent content = new LicenseContent();
content.setHolder(holder);
content.setIssuer(issuer);
content.setConsumerType("User");
content.setConsumerAmount(1);
content.setInfo(props.toString());
content.setSubject(SUBJECT);
java.util.Calendar cal =java.util.Calendar.getInstance();
cal.set(2006,1,1);
content.setNotAfter(cal.getTime());
manager.store(content, certFile);
}

private static final void addAttribute(
final StringBuffer dn,
final String oid,
final Properties props,
final String key) {
addAttribute(dn, oid, props.getProperty(key));
}

private static void addAttribute(
final StringBuffer dn,
final String oid,
String value) {
if (value == null) {
return;
}

final String trimmedValue = value.trim();
if ("".equals(trimmedValue)) {
return;
}

// See http://www.ietf.org/rfc/rfc2253.txt boolean quote = false;
if (!value.equals(trimmedValue)) {
quote = true;
}
else if (value.matches(".*[+,;<>/"].*")) {
;
}
quote = true;

if (dn.length() != 0) {
dn.append(',');
}
dn.append(oid);
dn.append('=');
if (quote) {
dn.append('"');
}
// Replace every single backslash with two backslashes
// whereas both parameters are expressed as regular expressions.
value = value.replaceAll("////", "////////");
// Replace every single quote with an escaped quote
// whereas both parameters are expressed as regular expressions.
value = value.replaceAll("/"", "/////"");
dn.append(value);
if (quote) {
dn.append('"');
}
}

private static Properties readInput(String pathname) throws IOException {
Properties props = new EncodedProperties();
InputStream in = new FileInputStream(pathname);
try {
props.load(in);
}
catch (IllegalArgumentException iae) {
throw new BadInputException(iae);
}
finally {
in.close();
}

return props;
}

/**
* This is the main entry point for JAVA key generators. It processes the
* command line arguments, loads and parses the input file, calls the key
* generator and writes output files.
*
* JAVA Exceptions are handled and transformed into key generator error
* codes. Exception messages will be written to <code>args[1]</code> and
* display on the error console.
*/
public static int KeyMain(String args[]) {
args = new String[3];
args[0] = "license.properties";
args[1] = "license.status";
args[2] = "license.lic";

if (args.length != 3) {
System.err.println("Usage: <input> <output1> <output2>");

return ERC_BAD_ARGS;
}

int errorCode = ERC_ERROR;
PrintWriter out = new PrintWriter(System.err);
try {
try {
// Read input and get encoding
final Properties props = readInput(args[0]);
final String encoding
= props.getProperty(ENCODING_KEY, ENCODING_DEFAULT);

// Setup real output with encoding read from input file.
out = new PrintWriter(
new OutputStreamWriter(
new FileOutputStream(args[1]),
encoding));

// Validate input and generate key file.
generateLicense(props, new File(args[2]));

// Write status.
out.write(MIME_TYPE + ":" + DISPLAY_FILENAME);
}
catch (BadInputException bie) {
errorCode = ERC_BAD_INPUT;
throw bie;
}
catch (IOException ioe) {
errorCode = ERC_FILE_IO;
throw ioe;
}
catch (OutOfMemoryError oome) {
errorCode = ERC_MEMORY;
throw oome;
}
}
catch (Throwable t) {
out.println("Error #" + errorCode);
t.printStackTrace(out);

return errorCode;
}
finally {
out.close();
}

return ERC_SUCCESS_BIN;
}

/**
* NOTE: This main() method is never called by the actual key server. It is
* just useful for debugging the key generator.
*/
public static final void main(String args[]) {
KeyMain(args);
/*try{
manager.install(new java.io.File("swutil.log"));
System.out.println("subject=" + manager.verify().getSubject());
System.exit(0);
}catch(Exception ex){
ex.printStackTrace();
}*/
}

public static class EncodedProperties
extends Properties {
public EncodedProperties() {
this(new Properties());
}

/**
* @throws NullPointerException if <tt>defaults</tt> is <tt>null</tt>.
*/
public EncodedProperties(Properties defaults) {
super(defaults);

// Make sure we have a proper default for the encoding.
defaults.setProperty(ENCODING_KEY, ENCODING_DEFAULT);
}

public void load(InputStream inStream) throws IOException {
super.load(inStream);

String encoding = super.getProperty(ENCODING_KEY);
if (ENCODING_PROPERTIES.equals(encoding)) {
return;
}

// Convert properties
try {
Map.Entry[] entries = new Map.Entry[entrySet().size()];
entrySet().toArray(entries);
for (int i = entries.length; --i >= 0; ) {
Map.Entry entry = entries[i];
String value = (String) entry.getValue();
value = new String(value.getBytes(ENCODING_PROPERTIES),
encoding);
setProperty( (String) entry.getKey(), value);
}
}
catch (UnsupportedEncodingException ignored) {}
}
}

public static class BadInputException
extends IOException {
public BadInputException(String message) {
super(message);
}

public BadInputException(Throwable cause) {
initCause(cause);
}
}

}

客户端程序安装license以及检验license合法性的代码:


安全警告[/b]
不要把私匙库拷贝到客户端,而只拷贝公匙库,要不然黑客就可以用你的私匙库来生成许许多多的license了
package com.sourceware.cmvp.license;

import de.schlichtherle.license.*;
import java.io.*;
import java.util.*;
import javax.security.auth.x500.X500Principal;
import java.util.prefs.Preferences;

/**
* <p>Title: CMVP通用媒体增值业务平台</p>
*
* <p>Description: CMVP通用媒体增值业务平台</p>
*
* <p>Copyright: Copyright (c) 2005</p>
*
* <p>Company: source-ware.com inc.</p>
*
* @author 黑山
* @version 2.0
*/
public class CMVPLicenseManager {
public CMVPLicenseManager() {
}

/** The product id of your software */
public static final String PRODUCT_ID = "cmvp20"; // CUSTOMIZE

/**
* The subject for the license manager and also the alias of the private
* key entry in the keystore.
*/
public static final String SUBJECT = "别名"; // CUSTOMIZE

/** The resource name of your private keystore file. */
public static final String KEYSTORE_RESOURCE = "公匙库文件名"; // CUSTOMIZE

/** The password for the keystore. */
public static final String KEYSTORE_STORE_PWD = "公匙库密码"; // CUSTOMIZE

/** The password to encrypt the generated license key file. */
public static final String CIPHER_KEY_PWD = "license文件密码"; // CUSTOMIZE

protected static final LicenseManager manager = new LicenseManager(
new DefaultLicenseParam(
SUBJECT,
Preferences.userNodeForPackage(CMVPLicenseManager.class),
new DefaultKeyStoreParam(
CMVPLicenseManager.class, // CUSTOMIZE
KEYSTORE_RESOURCE,
SUBJECT,
KEYSTORE_STORE_PWD,
null),//这里一定要是null
new DefaultCipherParam(CIPHER_KEY_PWD)));

/**
* NOTE: This main() method is never called by the actual key server. It is
* just useful for debugging the key generator.
*/
public static final void main(String args[]) {
try {

manager.install(new java.io.File("license.lic"));
String subject = manager.verify().getSubject();
System.out.println("subject========"+subject);
}
catch (Exception ex) {
ex.printStackTrace();
}
}

}
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
相关文章推荐