view org.eclipse.osgi/supplement/src/org/eclipse/osgi/util/NLS.d @ 87:8594250b1d1c

make it all again compile
author Frank Benoit <benoit@tionex.de>
date Sat, 18 Apr 2009 14:20:15 +0200
parents 0628aaa2996c
children bbe49769ec18
line wrap: on
line source

/*******************************************************************************
 * Copyright (c) 2005, 2008 IBM Corporation and others.
 * All rights reserved. This program and the accompanying materials
 * are made available under the terms of the Eclipse Public License v1.0
 * which accompanies this distribution, and is available at
 * http://www.eclipse.org/legal/epl-v10.html
 *
 * Contributors:
 *     IBM - Initial API and implementation
 * Port to the D programming language:
 *     Frank Benoit <benoit@tionex.de>
 *******************************************************************************/
module org.eclipse.osgi.util.NLS;

import java.lang.all;

// import java.io.IOException;
// import java.io.InputStream;
// import java.lang.reflect.Field;
// import java.lang.reflect.Modifier;
// import java.security.AccessController;
// import java.security.PrivilegedAction;
// import java.util.ArrayList;
// import java.util.HashMap;
// import java.util.Locale;
// import java.util.Map;
// import java.util.Properties;
//
// import org.eclipse.osgi.framework.debug.Debug;
// import org.eclipse.osgi.framework.log.FrameworkLog;
// import org.eclipse.osgi.framework.log.FrameworkLogEntry;

/**
 * Common superclass for all message bundle classes.  Provides convenience
 * methods for manipulating messages.
 * <p>
 * The <code>#bind</code> methods perform string substitution and should be considered a
 * convenience and <em>not</em> a full substitute replacement for <code>MessageFormat#format</code>
 * method calls.
 * </p>
 * <p>
 * Text appearing within curly braces in the given message, will be interpreted
 * as a numeric index to the corresponding substitution object in the given array. Calling
 * the <code>#bind</code> methods with text that does not map to an integer will result in an
 * {@link IllegalArgumentException}.
 * </p>
 * <p>
 * Text appearing within single quotes is treated as a literal. A single quote is escaped by
 * a preceeding single quote.
 * </p>
 * <p>
 * Clients who wish to use the full substitution power of the <code>MessageFormat</code> class should
 * call that class directly and not use these <code>#bind</code> methods.
 * </p>
 * <p>
 * Clients may subclass this type.
 * </p>
 *
 * @since 3.1
 */
public abstract class NLS {

//     private static final Object[] EMPTY_ARGS = new Object[0];
//     private static final String EXTENSION = ".properties"; //$NON-NLS-1$
//     private static String[] nlSuffixes;
//     /*
//      * NOTE do not change the name of this field; it is set by the Framework using reflection
//      */
//     private static FrameworkLog frameworkLog;
//
//     static final int SEVERITY_ERROR = 0x04;
//     static final int SEVERITY_WARNING = 0x02;
//     /*
//      * This object is assigned to the value of a field map to indicate
//      * that a translated message has already been assigned to that field.
//      */
//     static final Object ASSIGNED = new Object();
//
//     /**
//      * Creates a new NLS instance.
//      */
//     protected NLS() {
//         super();
//     }

    /**
     * Bind the given message's substitution locations with the given string value.
     *
     * @param message the message to be manipulated
     * @param binding the object to be inserted into the message
     * @return the manipulated String
     * @throws IllegalArgumentException if the text appearing within curly braces in the given message does not map to an integer
     */
    public static String bind(String message, Object binding) {
        implMissing( __FILE__, __LINE__ );
        return null;
//         return internalBind(message, null, String.valueOf(binding), null);
    }
    public static String bind(String message, String binding) {
        implMissing( __FILE__, __LINE__ );
        return null;
//         return internalBind(message, null, String.valueOf(binding), null);
    }

    /**
     * Bind the given message's substitution locations with the given string values.
     *
     * @param message the message to be manipulated
     * @param binding1 An object to be inserted into the message
     * @param binding2 A second object to be inserted into the message
     * @return the manipulated String
     * @throws IllegalArgumentException if the text appearing within curly braces in the given message does not map to an integer
     */
    public static String bind(String message, Object binding1, Object binding2) {
        implMissing( __FILE__, __LINE__ );
        return null;
//         return internalBind(message, null, String.valueOf(binding1), String.valueOf(binding2));
    }
    public static String bind(String message, String binding1, String binding2) {
        implMissing( __FILE__, __LINE__ );
        return null;
//         return internalBind(message, null, String.valueOf(binding1), String.valueOf(binding2));
    }

    /**
     * Bind the given message's substitution locations with the given string values.
     *
     * @param message the message to be manipulated
     * @param bindings An array of objects to be inserted into the message
     * @return the manipulated String
     * @throws IllegalArgumentException if the text appearing within curly braces in the given message does not map to an integer
     */
    public static String bind(String message, Object[] bindings) {
        implMissing( __FILE__, __LINE__ );
        return null;
//         return internalBind(message, bindings, null, null);
    }
    public static String bind(String message, String[] bindings) {
        implMissing( __FILE__, __LINE__ );
        return null;
//         return internalBind(message, bindings, null, null);
    }

//     /**
//      * Initialize the given class with the values from the specified message bundle.
//      *
//      * @param bundleName fully qualified path of the class name
//      * @param clazz the class where the constants will exist
//      */
//     public static void initializeMessages(final String bundleName, final Class clazz) {
//         if (System.getSecurityManager() is null) {
//             load(bundleName, clazz);
//             return;
//         }
//         AccessController.doPrivileged(new PrivilegedAction() {
//             public Object run() {
//                 load(bundleName, clazz);
//                 return null;
//             }
//         });
//     }
//
//     /*
//      * Perform the string substitution on the given message with the specified args.
//      * See the class comment for exact details.
//      */
//     private static String internalBind(String message, Object[] args, String argZero, String argOne) {
//         if (message is null)
//             return "No message available."; //$NON-NLS-1$
//         if (args is null || args.length is 0)
//             args = EMPTY_ARGS;
//
//         int length = message.length();
//         //estimate correct size of string buffer to avoid growth
//         int bufLen = length + (args.length * 5);
//         if (argZero !is null)
//             bufLen += argZero.length() - 3;
//         if (argOne !is null)
//             bufLen += argOne.length() - 3;
//         StringBuffer buffer = new StringBuffer(bufLen < 0 ? 0 : bufLen);
//         for (int i = 0; i < length; i++) {
//             char c = message.charAt(i);
//             switch (c) {
//                 case '{' :
//                     int index = message.indexOf('}', i);
//                     // if we don't have a matching closing brace then...
//                     if (index is -1) {
//                         buffer.append(c);
//                         break;
//                     }
//                     i++;
//                     if (i >= length) {
//                         buffer.append(c);
//                         break;
//                     }
//                     // look for a substitution
//                     int number = -1;
//                     try {
//                         number = Integer.parseInt(message.substring(i, index));
//                     } catch (NumberFormatException e) {
//                         throw new IllegalArgumentException();
//                     }
//                     if (number is 0 && argZero !is null)
//                         buffer.append(argZero);
//                     else if (number is 1 && argOne !is null)
//                         buffer.append(argOne);
//                     else {
//                         if (number >= args.length || number < 0) {
//                             buffer.append("<missing argument>"); //$NON-NLS-1$
//                             i = index;
//                             break;
//                         }
//                         buffer.append(args[number]);
//                     }
//                     i = index;
//                     break;
//                 case '\'' :
//                     // if a single quote is the last char on the line then skip it
//                     int nextIndex = i + 1;
//                     if (nextIndex >= length) {
//                         buffer.append(c);
//                         break;
//                     }
//                     char next = message.charAt(nextIndex);
//                     // if the next char is another single quote then write out one
//                     if (next is '\'') {
//                         i++;
//                         buffer.append(c);
//                         break;
//                     }
//                     // otherwise we want to read until we get to the next single quote
//                     index = message.indexOf('\'', nextIndex);
//                     // if there are no more in the string, then skip it
//                     if (index is -1) {
//                         buffer.append(c);
//                         break;
//                     }
//                     // otherwise write out the chars inside the quotes
//                     buffer.append(message.substring(nextIndex, index));
//                     i = index;
//                     break;
//                 default :
//                     buffer.append(c);
//             }
//         }
//         return buffer.toString();
//     }
//
//     /*
//      * Build an array of property files to search.  The returned array contains
//      * the property fields in order from most specific to most generic.
//      * So, in the FR_fr locale, it will return file_fr_FR.properties, then
//      * file_fr.properties, and finally file.properties.
//      */
//     private static String[] buildVariants(String root) {
//         if (nlSuffixes is null) {
//             //build list of suffixes for loading resource bundles
//             String nl = Locale.getDefault().toString();
//             ArrayList result = new ArrayList(4);
//             int lastSeparator;
//             while (true) {
//                 result.add('_' + nl + EXTENSION);
//                 lastSeparator = nl.lastIndexOf('_');
//                 if (lastSeparator is -1)
//                     break;
//                 nl = nl.substring(0, lastSeparator);
//             }
//             //add the empty suffix last (most general)
//             result.add(EXTENSION);
//             nlSuffixes = (String[]) result.toArray(new String[result.size()]);
//         }
//         root = root.replace('.', '/');
//         String[] variants = new String[nlSuffixes.length];
//         for (int i = 0; i < variants.length; i++)
//             variants[i] = root + nlSuffixes[i];
//         return variants;
//     }
//
//     private static void computeMissingMessages(String bundleName, Class clazz, Map fieldMap, Field[] fieldArray, bool isAccessible) {
//         // iterate over the fields in the class to make sure that there aren't any empty ones
//         final int MOD_EXPECTED = Modifier.PUBLIC | Modifier.STATIC;
//         final int MOD_MASK = MOD_EXPECTED | Modifier.FINAL;
//         final int numFields = fieldArray.length;
//         for (int i = 0; i < numFields; i++) {
//             Field field = fieldArray[i];
//             if ((field.getModifiers() & MOD_MASK) !is MOD_EXPECTED)
//                 continue;
//             //if the field has a a value assigned, there is nothing to do
//             if (fieldMap.get(field.getName()) is ASSIGNED)
//                 continue;
//             try {
//                 // Set a value for this empty field. We should never get an exception here because
//                 // we know we have a public static non-final field. If we do get an exception, silently
//                 // log it and continue. This means that the field will (most likely) be un-initialized and
//                 // will fail later in the code and if so then we will see both the NPE and this error.
//                 String value = "NLS missing message: " + field.getName() + " in: " + bundleName; //$NON-NLS-1$ //$NON-NLS-2$
//                 if (Debug.DEBUG_MESSAGE_BUNDLES)
//                     System.out.println(value);
//                 log(SEVERITY_WARNING, value, null);
//                 if (!isAccessible)
//                     field.setAccessible(true);
//                 field.set(null, value);
//             } catch (Exception e) {
//                 log(SEVERITY_ERROR, "Error setting the missing message value for: " + field.getName(), e); //$NON-NLS-1$
//             }
//         }
//     }
//
//     /*
//      * Load the given resource bundle using the specified class loader.
//      */
//     static void load(final String bundleName, Class clazz) {
//         long start = System.currentTimeMillis();
//         final Field[] fieldArray = clazz.getDeclaredFields();
//         ClassLoader loader = clazz.getClassLoader();
//
//         bool isAccessible = (clazz.getModifiers() & Modifier.PUBLIC) !is 0;
//
//         //build a map of field names to Field objects
//         final int len = fieldArray.length;
//         Map fields = new HashMap(len * 2);
//         for (int i = 0; i < len; i++)
//             fields.put(fieldArray[i].getName(), fieldArray[i]);
//
//         // search the variants from most specific to most general, since
//         // the MessagesProperties.put method will mark assigned fields
//         // to prevent them from being assigned twice
//         final String[] variants = buildVariants(bundleName);
//         for (int i = 0; i < variants.length; i++) {
//             // loader is null if we're launched off the Java boot classpath
//             final InputStream input = loader is null ? ClassLoader.getSystemResourceAsStream(variants[i]) : loader.getResourceAsStream(variants[i]);
//             if (input is null)
//                 continue;
//             try {
//                 final MessagesProperties properties = new MessagesProperties(fields, bundleName, isAccessible);
//                 properties.load(input);
//             } catch (IOException e) {
//                 log(SEVERITY_ERROR, "Error loading " + variants[i], e); //$NON-NLS-1$
//             } finally {
//                 if (input !is null)
//                     try {
//                         input.close();
//                     } catch (IOException e) {
//                         // ignore
//                     }
//             }
//         }
//         computeMissingMessages(bundleName, clazz, fields, fieldArray, isAccessible);
//         if (Debug.DEBUG_MESSAGE_BUNDLES)
//             System.out.println("Time to load message bundle: " + bundleName + " was " + (System.currentTimeMillis() - start) + "ms."); //$NON-NLS-1$ //$NON-NLS-2$ //$NON-NLS-3$
//     }
//
//     /*
//      * The method adds a log entry based on the error message and exception.
//      * The output is written to the System.err.
//      *
//      * This method is only expected to be called if there is a problem in
//      * the NLS mechanism. As a result, translation facility is not available
//      * here and messages coming out of this log are generally not translated.
//      *
//      * @param severity - severity of the message (SEVERITY_ERROR or SEVERITY_WARNING)
//      * @param message - message to log
//      * @param e - exception to log
//      */
//     static void log(int severity, String message, Exception e) {
//         if (frameworkLog !is null) {
//             frameworkLog.log(new FrameworkLogEntry("org.eclipse.osgi", severity, 1, message, 0, e, null)); //$NON-NLS-1$
//             return;
//         }
//         String statusMsg;
//         switch (severity) {
//             case SEVERITY_ERROR :
//                 statusMsg = "Error: "; //$NON-NLS-1$
//                 break;
//             case SEVERITY_WARNING :
//                 // intentionally fall through:
//             default :
//                 statusMsg = "Warning: "; //$NON-NLS-1$
//         }
//         if (message !is null)
//             statusMsg += message;
//         if (e !is null)
//             statusMsg += ": " + e.getMessage(); //$NON-NLS-1$
//         System.err.println(statusMsg);
//         if (e !is null)
//             e.printStackTrace();
//     }
//
//     /*
//      * Class which sub-classes java.util.Properties and uses the #put method
//      * to set field values rather than storing the values in the table.
//      */
//     private static class MessagesProperties extends Properties {
//
//         private static final int MOD_EXPECTED = Modifier.PUBLIC | Modifier.STATIC;
//         private static final int MOD_MASK = MOD_EXPECTED | Modifier.FINAL;
//         private static final long serialVersionUID = 1L;
//
//         private final String bundleName;
//         private final Map fields;
//         private final bool isAccessible;
//
//         public MessagesProperties(Map fieldMap, String bundleName, bool isAccessible) {
//             super();
//             this.fields = fieldMap;
//             this.bundleName = bundleName;
//             this.isAccessible = isAccessible;
//         }
//
//         /* (non-Javadoc)
//          * @see java.util.Hashtable#put(java.lang.Object, java.lang.Object)
//          */
//         public synchronized Object put(Object key, Object value) {
//             Object fieldObject = fields.put(key, ASSIGNED);
//             // if already assigned, there is nothing to do
//             if (fieldObject is ASSIGNED)
//                 return null;
//             if (fieldObject is null) {
//                 final String msg = "NLS unused message: " + key + " in: " + bundleName;//$NON-NLS-1$ //$NON-NLS-2$
//                 if (Debug.DEBUG_MESSAGE_BUNDLES)
//                     System.out.println(msg);
//                 log(SEVERITY_WARNING, msg, null);
//                 return null;
//             }
//             final Field field = (Field) fieldObject;
//             //can only set value of public static non-final fields
//             if ((field.getModifiers() & MOD_MASK) !is MOD_EXPECTED)
//                 return null;
//             try {
//                 // Check to see if we are allowed to modify the field. If we aren't (for instance
//                 // if the class is not public) then change the accessible attribute of the field
//                 // before trying to set the value.
//                 if (!isAccessible)
//                     field.setAccessible(true);
//                 // Set the value into the field. We should never get an exception here because
//                 // we know we have a public static non-final field. If we do get an exception, silently
//                 // log it and continue. This means that the field will (most likely) be un-initialized and
//                 // will fail later in the code and if so then we will see both the NPE and this error.
//                 field.set(null, value);
//             } catch (Exception e) {
//                 log(SEVERITY_ERROR, "Exception setting field value.", e); //$NON-NLS-1$
//             }
//             return null;
//         }
//     }
}