-
Notifications
You must be signed in to change notification settings - Fork 1
Expand file tree
/
Copy pathREADME
More file actions
240 lines (175 loc) · 9.95 KB
/
Copy pathREADME
File metadata and controls
240 lines (175 loc) · 9.95 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
The Buzz Media common-lib
http://www.thebuzzmedia.com/software/common-lib-common-java-utility-library/
Changelog
---------
2.3
* Added StreamUtils to make processing streams for their content easier.
* Added FailedTaskException to be able to reported the reason of a failed
task in more depth to the caller. Now AbstractRetryableTask is specified to
throw RuntimeExceptions in the case of fundamental errors (like thread
interruption) but to throw this new type any time a task fails to complete.
* Modified AbstractRetryableTask behavior when a sleeping thread is interrupted
by having it gracefully exit instead of throwing a RuntimeException.
A task being interrupted is an expected event if the task is being executed by
an ExecutorService that just had shutdownNow() called on it; throwing an
exception in response to this event was inappropriate.
* In addition to the interruption behavior, AbstractRetryableTask was
enhanced by adding an "isInterrupted()" state so the caller can tell if their
task completed normally OR if the executing thread was interrupted and that
is why the call() method returned.
If the caller cares, they can choose to retry the task (overcoming the interruption)
or if they expected the interruption (shutting down an ExecutorService) then
they can gracefully continue exiting.
* Modified AbstractRetryableTask to retry a default of 5 times instead of 3.
* Added "retryAttempt" value to callImpl making it easier for call implementation
to tell if they have run before and which attempt they are on.
* Corrected the retry count logic in AbsractRetryableTask.
* Added OAuthSigner class which provides core OAuth-spec-compliant functionality
like helping with the signature/HMAC generation.
* OAuthSigner.Algorithm defines support for MD5, SHA-1, SHA-256 and SHA-512
hashing when generating signatures.
* Added the "escape" sub-package with direct copies of the 4 escaping class
implementations from Google's API Client Library.
This was necessary for the OAuthSigner to generate correct signatures, using
the embedded URLEncoder from the JDK does not perform the encoding that the
OAuth spec requires (slightly modified version of RFC-3629).
The 4 classes were pulled in instead of adding the 240kb JAR as a dependency
for this library.
* Added iHarder's Base64 implementation (required by OAuthSigner)
http://iharder.sourceforge.net/current/java/base64/
This is a superior Base64 Java implementation utilized by the OAuthSigner class
and I wanted to avoid shipping a new JAR dependency. Since iHarder is only a
single, well-designed class with a wide-open license, I felt it was easier
(and more convenient) to simply add it to the library as-is to the benefit
of anyone else needing a Base64 implementation.
The class is clearly documented as being directly transplanted from the
iHarder Base64 project; all credit should be directed to Robert Harder
(rob@iharder.net) for this class.
* Changed "tbm.common.util.decode.maxBufferSize" and "tbm.common.util.encode.maxBufferSize"
property names by dropping the ".util" middle portion.
2.2
* Added IInput input definition.
IInput represents a powerful way to wrap any kind of readable input with a
common, generics-enhanced interface and read from it given a target buffer.
IInputs are a unifying structure at a higher level than similar approaches
like InputStream, Reader or even NIO's Buffer classes. None of these existing
approaches to abstracting sources of input can be used to wrap/represent
each other directly, which is why IInputs were created.
IInputs also allow for the controlling or "bounding" of accessible data from
an underlying source as well as automatically filling the read buffer from
the underlying source (regardless of type) making IInputs incredibly ease to
use as extremely efficient input sources.
* IInput implementations are as efficient as the most efficient read operations
from InputStream or NIO Buffer classes in that you get direct access to the
read buffer used by the stream to pull in data from it's underlying source;
there is no need to copy the contents to a second construct for use.
* Default IInput implementations provided for all popular sources:
* InputStreamInput java.io.InputStream source with byte[] buffer
* ReaderInput java.io.Reader source with char[] buffer
* ByteArrayInput byte[] source with byte[] buffer
* CharArrayInput char[] source with char[] buffer
* ByteBufferInput java.nio.ByteBuffer source with byte[] buffer
* CharBufferInput java.nio.CharBuffer source with char[] buffer
* CharSequenceInput java.lang.CharSequence source with char[] buffer
2.1
* Added AbstractRetryableTask; an Callable<V> implementation that can
automatically retry failed tasks up to a configurable amount of times,
sleeping the executing Thread a configurable (increasing) duration every
subsequent time the task fails. This is fantastic for cloud-based/API or
data-store operations that may frequently fail and retrying them is not
uncommon (e.g. Using Amazon Web Services APIs).
2.0
* Fixed bug in build script where library required Java 6. It now works under
Java 5 now.
* Added RandomUtils class. Convenience methods for generating random numeric
and character values (e.g. for password or unique file names).
* Added ArrayUtils "NoCheck" methods for all major index searches and equals
methods. These methods do NO pre-condition check. Handy when the utils class
is being used inside of another utils class that does all the pre-condition
checking already and don't want to incur any overhead.
* Added ArrayUtils.append methods
* Added ArrayUtils.insert methods
* Added ArrayUtils.indexAfter methods to find the first index after the given
value(s). Essentially skipping all values in array that match the value list
provided, and finding the first non-matching index after the group.
* Modified the ordering of arguments in library to more closely match the
sequence implied by language.
For example, when you see the method "indexOf(char c, chars[] array, int i)"
you can read that out loud as: "Find the indexOf 'c', in 'array' starting
at index 'i'".
Previously the ordering was arbitrary and non-uniform across the library. To
help improve the intuitiveness of the library and unify the style, it was
changed.
* Test coverage for all new methods and classes added.
* Integrated into production in the CloudFront Log Parser project.
http://www.thebuzzmedia.com/software/cloudfront-log-parser/
* Integrated into production in the common-parser-lib project.
http://www.thebuzzmedia.com/software/common-parser-lib-common-parser-java-utility-library/
1.1
* ArrayUtils additions
- equals
- ensureCapacity
- all methods apply to both byte[] and char[]
* Charset util additions
- Added DecodingUtils
- Added EncodingUtils
* Added test cases for all new methods and classes.
1.0
* Initial public release.
License
-------
This library is released under the Apache 2 License. See LICENSE.
Description
-----------
A collection of hand-tuned, low-overhead classes used by most of the open source
and commercial software from The Buzz Media.
Many of the operations performed by this library (like searching an array for
a byte or char, or parsing a non-float number) are performed by other libraries
readily available from projects like Apache Commons; this functionality is
re-implemented in this library with a tight focus on performance and lower
memory overhead at the expense of code duplication.
What that means is avoiding extremely deep method call-hierarchies for something
like indexOf(char[], char) calling down into a more specific method, then
another and another and another until finally ending up at some Abstract class
base implementation.
Benchmarks are provided to compare the library's performance to that of more
"standard" methods.
Performance
-----------
Benchmarks can be found in the /src/test/java folder and can be run directly
from the command line (no need to setup JUnit).
[Platform]
* Java 1.6.0_24 on Windows 7 64-bit
* Dual Core Intel E6850 processor
* 8 GB of ram
[Benchmark Results]
indexOf byte elapsed time: 12ms (3,328,000 bytes scanned)
indexOf byte[] elapsed time: 22ms (3,328,000 bytes scanned)
indexOfAny byte[] elapsed time: 23ms (3,328,000 bytes scanned)
JDK Integer.parseInt elapsed time: 72ms (1310720 numbers parsed, 6553600 bytes processed)
common-lib NumberUtils.parseInt elapsed time: 55ms (1310720 numbers parsed, 9175000 bytes processed)
** A note about the Integer.parseInt comparison; the time required to read in the
sample file, decode it from byte[] to char[] and then convert those all into
String instances IS NOT INCLUDED in the benchmark timing. If you were to include
that, you would see both the memory usage and CPU time of using
Integer.parseInt to be significantly higher than NumberUtils.parseInt.
Runtime Requirements
--------------------
None.
There are currently no 3rd party dependencies required to use common-lib.
History
-------
While working on a few disparate projects (high performance XML parser,
Redis DB driver, CloudFront log parser, etc.) I noticed a pattern in the types
of utilities I was writing over and over again OR logic I was inlining directly
in my code.
I generalized this code and broke it out into this library so the handful of
projects maintained by The Buzz Media could more easily make use of the code.
I decided to open source the project because there is no proprietary magic in
any of this, the library is tuned to be fast with a small memory footprint and
I thought others might find it handy as opposed to using more bloated libs like
Apache Commons.
Contact
-------
If you have questions, comments or bug reports for this software please contact
us at: software@thebuzzmedia.com