added better comments
This commit is contained in:
@@ -198,8 +198,8 @@ public final class SQL implements Appendable{
|
|||||||
/** fills params list with non-trivial parameters.
|
/** fills params list with non-trivial parameters.
|
||||||
* we place this method here to be as close as possible to the one which generates the sql code.
|
* we place this method here to be as close as possible to the one which generates the sql code.
|
||||||
* check and check_export must be in synch.
|
* check and check_export must be in synch.
|
||||||
* @param filter
|
* @param filter check operation to perform over conditions.
|
||||||
* @param params
|
* @param params extracted params.
|
||||||
*/
|
*/
|
||||||
public final void check_export(Check filter,List<Object> params) {
|
public final void check_export(Check filter,List<Object> params) {
|
||||||
if(filter.isLeaf()){
|
if(filter.isLeaf()){
|
||||||
|
|||||||
@@ -132,8 +132,8 @@ public class SQLCleaner implements Closeable{
|
|||||||
}
|
}
|
||||||
/**
|
/**
|
||||||
* This calls one delete. It can and is called from outside in case of nesting when link is external.
|
* This calls one delete. It can and is called from outside in case of nesting when link is external.
|
||||||
* @param rec
|
* @param rec database object to delete
|
||||||
* @throws SQLException
|
* @throws SQLException sql related error
|
||||||
*/
|
*/
|
||||||
public boolean deleteRecord(DBO rec) throws SQLException{
|
public boolean deleteRecord(DBO rec) throws SQLException{
|
||||||
if(rec==null) return false;
|
if(rec==null) return false;
|
||||||
|
|||||||
@@ -160,7 +160,8 @@ public class SQLTerminal implements Terminal{
|
|||||||
/**
|
/**
|
||||||
* Returns back java class for given id and or name.
|
* Returns back java class for given id and or name.
|
||||||
* The name is not used in default implementation.
|
* The name is not used in default implementation.
|
||||||
* @param typeid
|
* @param typeid sql type to map
|
||||||
|
* @return Class matching sql typeid.
|
||||||
*/
|
*/
|
||||||
public Class<?> getJavaType(int typeid) {
|
public Class<?> getJavaType(int typeid) {
|
||||||
Class<?> ret=getSQL2Java().get(typeid);
|
Class<?> ret=getSQL2Java().get(typeid);
|
||||||
|
|||||||
@@ -8,10 +8,7 @@ You may not use this file except in compliance with the License.
|
|||||||
|
|
||||||
package com.reliancy.jabba;
|
package com.reliancy.jabba;
|
||||||
|
|
||||||
import java.io.File;
|
|
||||||
import java.io.IOException;
|
import java.io.IOException;
|
||||||
import java.util.logging.Logger;
|
|
||||||
|
|
||||||
import com.reliancy.dbo.Terminal;
|
import com.reliancy.dbo.Terminal;
|
||||||
import com.reliancy.jabba.sec.SecurityPolicy;
|
import com.reliancy.jabba.sec.SecurityPolicy;
|
||||||
import com.reliancy.util.CodeException;
|
import com.reliancy.util.CodeException;
|
||||||
|
|||||||
@@ -4,7 +4,6 @@ import java.io.File;
|
|||||||
import java.io.IOException;
|
import java.io.IOException;
|
||||||
import java.util.ArrayList;
|
import java.util.ArrayList;
|
||||||
import java.util.HashMap;
|
import java.util.HashMap;
|
||||||
import java.util.Iterator;
|
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
import java.util.Map;
|
import java.util.Map;
|
||||||
import java.util.logging.Logger;
|
import java.util.logging.Logger;
|
||||||
@@ -20,7 +19,6 @@ import com.reliancy.util.Log;
|
|||||||
*/
|
*/
|
||||||
public class ArgsConfig extends Config.Base{
|
public class ArgsConfig extends Config.Base{
|
||||||
final String[] args;
|
final String[] args;
|
||||||
final ArrayList<Property<?>> schema=new ArrayList<>();
|
|
||||||
String id;
|
String id;
|
||||||
public ArgsConfig(String... args){
|
public ArgsConfig(String... args){
|
||||||
this.args=args;
|
this.args=args;
|
||||||
@@ -166,26 +164,5 @@ public class ArgsConfig extends Config.Base{
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
|
||||||
public <T> Config setProperty(Property<T> key, T val) {
|
|
||||||
props.put(key,val);
|
|
||||||
return this;
|
|
||||||
}
|
|
||||||
@Override
|
|
||||||
public <T> T delProperty(Property<T> key) {
|
|
||||||
Object val=props.remove(key);
|
|
||||||
return key.getTyp().cast(val);
|
|
||||||
}
|
|
||||||
@Override
|
|
||||||
public Iterator<Property<?>> iterator() {
|
|
||||||
ArrayList<Property<?>> keys=new ArrayList<>(props.keySet());
|
|
||||||
return keys.iterator();
|
|
||||||
}
|
|
||||||
@Override
|
|
||||||
public Config setSchema(Property<?> ...p){
|
|
||||||
this.schema.clear();
|
|
||||||
for(Property<?> pp:p) schema.add(pp);
|
|
||||||
return this;
|
|
||||||
}
|
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -7,10 +7,11 @@ You may not use this file except in compliance with the License.
|
|||||||
*/
|
*/
|
||||||
package com.reliancy.jabba;
|
package com.reliancy.jabba;
|
||||||
import java.io.IOException;
|
import java.io.IOException;
|
||||||
|
import java.util.ArrayList;
|
||||||
import java.util.Collection;
|
import java.util.Collection;
|
||||||
import java.util.HashMap;
|
import java.util.HashMap;
|
||||||
|
import java.util.Iterator;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
import java.util.Set;
|
|
||||||
import java.util.TreeSet;
|
import java.util.TreeSet;
|
||||||
|
|
||||||
import org.slf4j.Logger;
|
import org.slf4j.Logger;
|
||||||
@@ -73,6 +74,7 @@ public interface Config extends Iterable<Config.Property<?>>{
|
|||||||
}
|
}
|
||||||
public static abstract class Base implements Config {
|
public static abstract class Base implements Config {
|
||||||
protected final HashMap<Property<?>,Object> props=new HashMap<>();
|
protected final HashMap<Property<?>,Object> props=new HashMap<>();
|
||||||
|
final ArrayList<Property<?>> schema=new ArrayList<>();
|
||||||
protected Object modified;
|
protected Object modified;
|
||||||
public boolean isModified(){
|
public boolean isModified(){
|
||||||
return modified!=null;
|
return modified!=null;
|
||||||
@@ -109,6 +111,17 @@ public interface Config extends Iterable<Config.Property<?>>{
|
|||||||
Object val=props.remove(key);
|
Object val=props.remove(key);
|
||||||
return key.getTyp().cast(val);
|
return key.getTyp().cast(val);
|
||||||
}
|
}
|
||||||
|
@Override
|
||||||
|
public Iterator<Property<?>> iterator() {
|
||||||
|
ArrayList<Property<?>> keys=new ArrayList<>(props.keySet());
|
||||||
|
return keys.iterator();
|
||||||
|
}
|
||||||
|
@Override
|
||||||
|
public Config importSchema(boolean do_clear,Property<?> ...p){
|
||||||
|
if(do_clear) this.schema.clear();
|
||||||
|
for(Property<?> pp:p) schema.add(pp);
|
||||||
|
return this;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public static final Property<String> LOG_LEVEL=new Property<>("LOG_LEVEL",String.class);
|
public static final Property<String> LOG_LEVEL=new Property<>("LOG_LEVEL",String.class);
|
||||||
@@ -130,6 +143,6 @@ public interface Config extends Iterable<Config.Property<?>>{
|
|||||||
public <T> Config setProperty(Property<T> key,T val);
|
public <T> Config setProperty(Property<T> key,T val);
|
||||||
public <T> T getProperty(Property<T> key,T def);
|
public <T> T getProperty(Property<T> key,T def);
|
||||||
public <T> T delProperty(Property<T> key);
|
public <T> T delProperty(Property<T> key);
|
||||||
public Config setSchema(Property<?> ...p);
|
public Config importSchema(boolean clear,Property<?> ...p);
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -8,12 +8,9 @@ You may not use this file except in compliance with the License.
|
|||||||
package com.reliancy.jabba;
|
package com.reliancy.jabba;
|
||||||
|
|
||||||
import java.io.IOException;
|
import java.io.IOException;
|
||||||
import java.util.ArrayList;
|
|
||||||
import java.util.Iterator;
|
|
||||||
|
|
||||||
public class FileConfig extends Config.Base{
|
public class FileConfig extends Config.Base{
|
||||||
final Config parent;
|
final Config parent;
|
||||||
final ArrayList<Property<?>> schema=new ArrayList<>();
|
|
||||||
String path;
|
String path;
|
||||||
public FileConfig(Config parent,String p){
|
public FileConfig(Config parent,String p){
|
||||||
this.parent=parent;
|
this.parent=parent;
|
||||||
@@ -22,9 +19,9 @@ public class FileConfig extends Config.Base{
|
|||||||
public FileConfig(String p){
|
public FileConfig(String p){
|
||||||
this(null,p);
|
this(null,p);
|
||||||
}
|
}
|
||||||
public Config clear(){
|
@Override
|
||||||
props.clear();
|
public String getId() {
|
||||||
return this;
|
return path;
|
||||||
}
|
}
|
||||||
@Override
|
@Override
|
||||||
public Config getParent(){
|
public Config getParent(){
|
||||||
@@ -41,10 +38,6 @@ public class FileConfig extends Config.Base{
|
|||||||
return this;
|
return this;
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
|
||||||
public String getId() {
|
|
||||||
return path;
|
|
||||||
}
|
|
||||||
public FileConfig setId(String path) {
|
public FileConfig setId(String path) {
|
||||||
this.path = path;
|
this.path = path;
|
||||||
return this;
|
return this;
|
||||||
@@ -72,28 +65,6 @@ public class FileConfig extends Config.Base{
|
|||||||
return def;
|
return def;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
/**
|
|
||||||
* FileConfig will save property localy so it is perserved even if not later provided.
|
|
||||||
*/
|
|
||||||
@Override
|
|
||||||
public <T> Config setProperty(Config.Property<T> key, T val) {
|
|
||||||
props.put(key,val);
|
|
||||||
return this;
|
|
||||||
}
|
|
||||||
@Override
|
|
||||||
public <T> T delProperty(Property<T> key) {
|
|
||||||
return (T)props.remove(key);
|
|
||||||
}
|
|
||||||
@Override
|
|
||||||
public Iterator<Property<?>> iterator() {
|
|
||||||
ArrayList<Property<?>> keys=new ArrayList<>(props.keySet());
|
|
||||||
return keys.iterator();
|
|
||||||
}
|
|
||||||
public Config setSchema(Property<?> ...p){
|
|
||||||
this.schema.clear();
|
|
||||||
for(Property<?> pp:p) schema.add(pp);
|
|
||||||
return this;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -158,9 +158,7 @@ public class FileServer extends EndPoint implements AppModule,Resources.PathRewr
|
|||||||
}
|
}
|
||||||
/** adds a route which serves files.
|
/** adds a route which serves files.
|
||||||
* if disk_path is ommited (0 len) or null we use Resources.search_path.
|
* if disk_path is ommited (0 len) or null we use Resources.search_path.
|
||||||
* @param url_path
|
* @param bucket resource holder to add
|
||||||
* @param f
|
|
||||||
* @param disk_path search path for resource
|
|
||||||
*/
|
*/
|
||||||
public final FileServer addBucket(Bucket bucket){
|
public final FileServer addBucket(Bucket bucket){
|
||||||
buckets.add(bucket);
|
buckets.add(bucket);
|
||||||
|
|||||||
@@ -7,7 +7,6 @@ You may not use this file except in compliance with the License.
|
|||||||
*/
|
*/
|
||||||
package com.reliancy.jabba;
|
package com.reliancy.jabba;
|
||||||
|
|
||||||
import java.io.File;
|
|
||||||
import java.io.IOException;
|
import java.io.IOException;
|
||||||
import java.util.EventListener;
|
import java.util.EventListener;
|
||||||
|
|
||||||
@@ -203,6 +202,25 @@ public class JettyApp extends App implements Handler{
|
|||||||
Log.cleanup(); // release logging in case we deferred
|
Log.cleanup(); // release logging in case we deferred
|
||||||
System.gc(); // sweep memory just in caser
|
System.gc(); // sweep memory just in caser
|
||||||
}
|
}
|
||||||
|
/** Registers a shutdown hook to interrup jetty.
|
||||||
|
* ctrl-c works but does not perform our shutdown sequence.
|
||||||
|
* this code interrupts jetty and then waits for app to finish.
|
||||||
|
*/
|
||||||
|
public void addShutdownHook(){
|
||||||
|
final JettyApp app=this;
|
||||||
|
Runtime.getRuntime().addShutdownHook(new Thread(() -> {
|
||||||
|
if(app.isRunning()){
|
||||||
|
try {
|
||||||
|
app.jetty.stop();
|
||||||
|
synchronized(app){
|
||||||
|
app.wait(5000);
|
||||||
|
}
|
||||||
|
} catch (Exception e) {
|
||||||
|
app.log().error("shutdown cleanup:", e);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}));
|
||||||
|
}
|
||||||
/** called from begin just before jetty starts.
|
/** called from begin just before jetty starts.
|
||||||
* this method is called before middleware is notified so we can add or adjust config.
|
* this method is called before middleware is notified so we can add or adjust config.
|
||||||
* override to hook up your application.
|
* override to hook up your application.
|
||||||
@@ -240,18 +258,7 @@ public class JettyApp extends App implements Handler{
|
|||||||
public static void main( String[] args ) throws Exception{
|
public static void main( String[] args ) throws Exception{
|
||||||
Config cnf=new ArgsConfig(args).load();
|
Config cnf=new ArgsConfig(args).load();
|
||||||
JettyApp app=new JettyApp();
|
JettyApp app=new JettyApp();
|
||||||
Runtime.getRuntime().addShutdownHook(new Thread(() -> {
|
app.addShutdownHook();
|
||||||
if(app.isRunning()){
|
|
||||||
try {
|
|
||||||
app.jetty.stop();
|
|
||||||
synchronized(app){
|
|
||||||
app.wait(5000);
|
|
||||||
}
|
|
||||||
} catch (Exception e) {
|
|
||||||
app.log().error("shutdown cleanup:", e);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}));
|
|
||||||
app.run(cnf);
|
app.run(cnf);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -21,7 +21,6 @@ import java.nio.charset.StandardCharsets;
|
|||||||
import java.text.MessageFormat;
|
import java.text.MessageFormat;
|
||||||
import java.util.Collection;
|
import java.util.Collection;
|
||||||
import java.util.Iterator;
|
import java.util.Iterator;
|
||||||
import java.util.Locale;
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* This class will replace the Java writer.
|
* This class will replace the Java writer.
|
||||||
|
|||||||
@@ -125,8 +125,9 @@ public class Hdr {
|
|||||||
}
|
}
|
||||||
/**
|
/**
|
||||||
* this version will get or create a slot by given name.
|
* this version will get or create a slot by given name.
|
||||||
* @param name
|
* @param name slot name
|
||||||
* @return
|
* @param make wether to create if not present
|
||||||
|
* @return Slot or null.
|
||||||
*/
|
*/
|
||||||
public Slot getSlot(String name,boolean make){
|
public Slot getSlot(String name,boolean make){
|
||||||
int index=indexOf(name);
|
int index=indexOf(name);
|
||||||
|
|||||||
@@ -17,6 +17,7 @@ import java.util.ArrayList;
|
|||||||
import java.util.Base64;
|
import java.util.Base64;
|
||||||
import java.util.Collection;
|
import java.util.Collection;
|
||||||
import java.util.HashMap;
|
import java.util.HashMap;
|
||||||
|
import java.util.Iterator;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
import java.util.Map;
|
import java.util.Map;
|
||||||
import java.util.Random;
|
import java.util.Random;
|
||||||
@@ -29,34 +30,57 @@ import java.util.zip.Inflater;
|
|||||||
*/
|
*/
|
||||||
public final class Handy {
|
public final class Handy {
|
||||||
public static final String WHITE=" \t\r\f\n";
|
public static final String WHITE=" \t\r\f\n";
|
||||||
/** place left-right around verb.*/
|
|
||||||
|
/** place left-right around verb.
|
||||||
|
* @param verb body of text
|
||||||
|
* @param left to add left of verb
|
||||||
|
* @param left to add right of verb
|
||||||
|
* @return adjusted text
|
||||||
|
* */
|
||||||
public static String wrap(String verb, String left, String right) {
|
public static String wrap(String verb, String left, String right) {
|
||||||
if(verb==null) verb="";
|
if(verb==null) verb="";
|
||||||
if(verb.startsWith(left) && verb.endsWith(right)) return verb;
|
if(verb.startsWith(left) && verb.endsWith(right)) return verb;
|
||||||
return left+verb.trim()+right;
|
return left+verb.trim()+right;
|
||||||
}
|
}
|
||||||
/** remove left-right around verb.*/
|
/** remove left-right around verb.
|
||||||
|
* @param verb body of text
|
||||||
|
* @param left to remove left of verb
|
||||||
|
* @param left to remove right of verb
|
||||||
|
* @return adjusted text
|
||||||
|
**/
|
||||||
public static String unwrap(String verb, String left, String right) {
|
public static String unwrap(String verb, String left, String right) {
|
||||||
if(verb==null) return verb;
|
if(verb==null) return verb;
|
||||||
String ret=verb.trim();
|
String ret=verb.trim();
|
||||||
if(verb.startsWith(left) && verb.endsWith(right)) ret=verb.substring(1,verb.length()-1);
|
if(ret.startsWith(left) && ret.endsWith(right)){
|
||||||
|
ret=ret.substring(left.length());
|
||||||
|
ret=ret.substring(0,ret.length()-right.length());
|
||||||
|
}
|
||||||
return ret;
|
return ret;
|
||||||
}
|
}
|
||||||
/** remove any chars elements from left of verb. */
|
/** remove any chars elements from left of verb.
|
||||||
|
* @param verb body of text
|
||||||
|
* @return adjusted text
|
||||||
|
*/
|
||||||
public static String trimLeft(String verb,String chars){
|
public static String trimLeft(String verb,String chars){
|
||||||
while(verb.length()>0 && chars.indexOf(verb.charAt(0))!=-1){
|
while(verb.length()>0 && chars.indexOf(verb.charAt(0))!=-1){
|
||||||
verb=verb.substring(1);
|
verb=verb.substring(1);
|
||||||
}
|
}
|
||||||
return verb;
|
return verb;
|
||||||
}
|
}
|
||||||
/** remove any chars elements from right of verb. */
|
/** remove any chars elements from right of verb.
|
||||||
|
* @param verb body of text
|
||||||
|
* @return adjusted text
|
||||||
|
*/
|
||||||
public static String trimRight(String verb,String chars){
|
public static String trimRight(String verb,String chars){
|
||||||
while(verb.length()>0 && chars.indexOf(verb.charAt(verb.length()-1))!=-1){
|
while(verb.length()>0 && chars.indexOf(verb.charAt(verb.length()-1))!=-1){
|
||||||
verb=verb.substring(0,verb.length()-1);
|
verb=verb.substring(0,verb.length()-1);
|
||||||
}
|
}
|
||||||
return verb;
|
return verb;
|
||||||
}
|
}
|
||||||
/** remove any chars elements from right and right of verb. */
|
/** remove any chars elements from right and right of verb.
|
||||||
|
* @param verb body of text
|
||||||
|
* @return adjusted text
|
||||||
|
*/
|
||||||
public static String trimBoth(String verb,String chars){
|
public static String trimBoth(String verb,String chars){
|
||||||
verb=trimLeft(verb, chars);
|
verb=trimLeft(verb, chars);
|
||||||
verb=trimRight(verb, chars);
|
verb=trimRight(verb, chars);
|
||||||
@@ -77,11 +101,10 @@ public final class Handy {
|
|||||||
public static <T> T nz(T val, T def){
|
public static <T> T nz(T val, T def){
|
||||||
return val!=null?val:def;
|
return val!=null?val:def;
|
||||||
}
|
}
|
||||||
/**
|
/** Convert incoming value to an expected class.
|
||||||
* Will try to convert incoming value to an expected class.
|
* @param clazz expected class
|
||||||
* @param clazz
|
* @param val observed value
|
||||||
* @param val
|
* @return val converted to type clazz.
|
||||||
* @return
|
|
||||||
*/
|
*/
|
||||||
public static Object normalize(Class<?> clazz, Object val ) {
|
public static Object normalize(Class<?> clazz, Object val ) {
|
||||||
if(val==null) return null; // we are null
|
if(val==null) return null; // we are null
|
||||||
@@ -145,7 +168,7 @@ public final class Handy {
|
|||||||
return digitCount>0;
|
return digitCount>0;
|
||||||
}
|
}
|
||||||
/**
|
/**
|
||||||
* returns true if the string is null, empty or contains only white space.
|
* @return true if the string is null, empty or contains only white space.
|
||||||
*/
|
*/
|
||||||
public static boolean isBlank(CharSequence str) {
|
public static boolean isBlank(CharSequence str) {
|
||||||
int strLen;
|
int strLen;
|
||||||
@@ -330,9 +353,9 @@ public final class Handy {
|
|||||||
/** Simple XOR encryption of a map of key-value pairs.
|
/** Simple XOR encryption of a map of key-value pairs.
|
||||||
* We randomize the order of key value pairs to make the string more unpredictable.
|
* We randomize the order of key value pairs to make the string more unpredictable.
|
||||||
* Returned string is base64 and web safe
|
* Returned string is base64 and web safe
|
||||||
* @param key
|
* @param key encryption key
|
||||||
* @param m
|
* @param m map of param-value pairs to encrypt values.
|
||||||
* @return a string of encoded map key-value pairs which were then encrypted
|
* @return a string of encoded map param-value pairs which were then encrypted
|
||||||
*/
|
*/
|
||||||
public static final String encrypt(String key,Map<String,String> m){
|
public static final String encrypt(String key,Map<String,String> m){
|
||||||
String ret=null;
|
String ret=null;
|
||||||
@@ -411,9 +434,9 @@ public final class Handy {
|
|||||||
}
|
}
|
||||||
/**
|
/**
|
||||||
* Generates a hash string with the algorithm name prefixed.
|
* Generates a hash string with the algorithm name prefixed.
|
||||||
* @param message
|
* @param message text to hash
|
||||||
* @param algorithm
|
* @param algorithm algorithm to use
|
||||||
* @return
|
* @return hash digest
|
||||||
*/
|
*/
|
||||||
public static String hashString(String message, String algorithm) throws NoSuchAlgorithmException, UnsupportedEncodingException{
|
public static String hashString(String message, String algorithm) throws NoSuchAlgorithmException, UnsupportedEncodingException{
|
||||||
if(message==null) return message;
|
if(message==null) return message;
|
||||||
@@ -421,6 +444,7 @@ public final class Handy {
|
|||||||
byte[] hashedBytes = digest.digest(message.getBytes("UTF-8"));
|
byte[] hashedBytes = digest.digest(message.getBytes("UTF-8"));
|
||||||
return algorithm.toLowerCase()+":"+encodeBase64(hashedBytes);
|
return algorithm.toLowerCase()+":"+encodeBase64(hashedBytes);
|
||||||
}
|
}
|
||||||
|
/** hash text using sha256. */
|
||||||
public static String hashSHA256(String message){
|
public static String hashSHA256(String message){
|
||||||
try{
|
try{
|
||||||
return hashString(message,"SHA-256");
|
return hashString(message,"SHA-256");
|
||||||
@@ -454,10 +478,10 @@ public final class Handy {
|
|||||||
/**
|
/**
|
||||||
* Finds first occurrence of sub inside body with and without case.
|
* Finds first occurrence of sub inside body with and without case.
|
||||||
* We implement this search via a FSM and ignore the case.
|
* We implement this search via a FSM and ignore the case.
|
||||||
* @param body
|
* @param body text to search
|
||||||
* @param sub
|
* @param sub subsequence to find
|
||||||
* @param offset
|
* @param offset offset from 0
|
||||||
* @return offset of first occurance
|
* @return offset of next occurance starting at offiset
|
||||||
*/
|
*/
|
||||||
public static final int indexOf(CharSequence body,CharSequence sub,int offset){
|
public static final int indexOf(CharSequence body,CharSequence sub,int offset){
|
||||||
if(body==null) return -1;
|
if(body==null) return -1;
|
||||||
@@ -479,6 +503,8 @@ public final class Handy {
|
|||||||
}
|
}
|
||||||
/**
|
/**
|
||||||
* Will trim the string from left and right and remove any of the symbols.
|
* Will trim the string from left and right and remove any of the symbols.
|
||||||
|
* @param trim text to strip
|
||||||
|
* @param sym set of characters to trim
|
||||||
*/
|
*/
|
||||||
public static String trim(String trim,String sym) {
|
public static String trim(String trim,String sym) {
|
||||||
if(trim==null || trim.length()==0) return trim;
|
if(trim==null || trim.length()==0) return trim;
|
||||||
@@ -557,5 +583,8 @@ public final class Handy {
|
|||||||
public static String[] split(String delim,String str) {
|
public static String[] split(String delim,String str) {
|
||||||
return split(delim,str,-1);
|
return split(delim,str,-1);
|
||||||
}
|
}
|
||||||
|
@SafeVarargs
|
||||||
|
public static <T> Iterator<T> chainIterators(Iterator<T>...its){
|
||||||
|
return new JointIterator<T>(its);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -0,0 +1,35 @@
|
|||||||
|
package com.reliancy.util;
|
||||||
|
|
||||||
|
import java.util.Iterator;
|
||||||
|
import java.util.NoSuchElementException;
|
||||||
|
|
||||||
|
/** Chains multiple iterators to act as one.
|
||||||
|
*
|
||||||
|
*/
|
||||||
|
public class JointIterator<T> implements Iterator<T> {
|
||||||
|
final Iterator<T> iterators[];
|
||||||
|
int cursor;
|
||||||
|
@SafeVarargs
|
||||||
|
public JointIterator(Iterator<T> ...its){
|
||||||
|
this.iterators=its;
|
||||||
|
cursor=0;
|
||||||
|
}
|
||||||
|
@Override
|
||||||
|
public boolean hasNext() {
|
||||||
|
while(cursor<iterators.length){
|
||||||
|
if(iterators[cursor].hasNext()) return true;
|
||||||
|
cursor+=1; // cursor exhausted got to next iterator
|
||||||
|
}
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public T next() {
|
||||||
|
if(cursor<iterators.length){
|
||||||
|
return iterators[cursor].next();
|
||||||
|
}else{
|
||||||
|
throw new NoSuchElementException();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
@@ -8,7 +8,6 @@ You may not use this file except in compliance with the License.
|
|||||||
|
|
||||||
package com.reliancy.util;
|
package com.reliancy.util;
|
||||||
import java.io.File;
|
import java.io.File;
|
||||||
import java.io.UnsupportedEncodingException;
|
|
||||||
import java.net.MalformedURLException;
|
import java.net.MalformedURLException;
|
||||||
import java.net.URL;
|
import java.net.URL;
|
||||||
import java.net.URLDecoder;
|
import java.net.URLDecoder;
|
||||||
|
|||||||
Reference in New Issue
Block a user