Skip to content

Commit

Permalink
refactored attachment support
Browse files Browse the repository at this point in the history
  • Loading branch information
Jan Schäfer committed Jan 24, 2015
1 parent 3e657b2 commit 05b531e
Show file tree
Hide file tree
Showing 23 changed files with 494 additions and 126 deletions.
Original file line number Diff line number Diff line change
@@ -1,13 +1,12 @@
package com.tngtech.jgiven;


import com.tngtech.jgiven.attachment.Attachment;

/**
* This interface can be injected into a stage by using the {@link com.tngtech.jgiven.annotation.ExpectedScenarioState}
* This interface can be injected into a stage by using the {@link com.tngtech.jgiven.annotation.ScenarioState}
* annotation. It provides programmatic access to the current executed step.
*/
public interface StepAccess {
public interface CurrentStep {

/**
* Adds an attachment to the current step
Expand All @@ -16,14 +15,6 @@ public interface StepAccess {
*/
void addAttachment( Attachment attachment );

/**
* Set the description of the current step
*
* @param description the description to set
* @see com.tngtech.jgiven.annotation.Description
*/
void setDescription( String description );

/**
* Set the extended description of the current step
*
Expand Down
Original file line number Diff line number Diff line change
@@ -1,10 +1,182 @@
package com.tngtech.jgiven.attachment;

import java.io.*;
import java.nio.charset.Charset;

import javax.xml.bind.DatatypeConverter;

import com.google.common.io.ByteStreams;
import com.google.common.io.CharStreams;
import com.google.common.io.Files;
import com.tngtech.jgiven.impl.util.ResourceUtil;

/**
* Represents an attachment of a step
* Represents an attachment of a step.
* Attachments must be representable as a String so that it can be stored as JSON.
* For binary attachments this means that they have to be encoded with Base64.
* In addition, attachments must have a media type so that reporters know
* how to present an attachment.
*
*/
public interface Attachment {
String asString();
public class Attachment {

/**
* An optional title.
* Can be {@code null}.
*/
private String title;

/**
* The content of the attachment.
* In case the media type is binary, this is a Base64 encoded string
*/
private final String content;

private final MediaType mediaType;

/**
* Convenience constructor, where title is set to {@code null}
*/
protected Attachment( String content, MediaType mediaType ) {
this( content, mediaType, null );
}

/**
* Creates a new instance of this Attachment
* @param content the content of this attachment. In case of a binary attachment, this must be
* Base64 encoded. Must not be {@code null}
* @param mediaType the mediaType. Must not be {@code null}
* @param title an optional title, may be {@code null}
*/
protected Attachment( String content, MediaType mediaType, String title ) {
if( mediaType == null ) {
throw new IllegalArgumentException( "MediaType must not be null" );
}

if( content == null ) {
throw new IllegalArgumentException( "Content must not be null" );
}

this.content = content;
this.mediaType = mediaType;
this.title = title;
}

/**
* An optional title of the attachment.
* The title can be used by reporters, e.g. as a tooltip.
* Can be {@code null}.
*/
public String title() {
return title;
}

/**
* The content of the attachment represented as a string.
* Binary attachments must be encoded in Base64 format.
*/
public String content() {
return content;
}

/**
* The type of the attachment.
* It depends on the reporter how this information is used.
*/
public MediaType getMediaType() {
return mediaType;
}

/**
* An optional title
*/
public String getTitle() {
return title;
}

/**
* Sets the title and returns {@code this}
*/
public Attachment withTitle( String title ) {
this.title = title;
return this;
}

/**
* Creates an attachment from a given array of bytes.
* The bytes will be Base64 encoded.
* @throws java.lang.IllegalArgumentException if mediaType is not binary
*/
public static Attachment fromBinaryBytes( byte[] bytes, MediaType mediaType ) {
if( !mediaType.isBinary() ) {
throw new IllegalArgumentException( "MediaType must be binary" );
}
return new Attachment( DatatypeConverter.printBase64Binary( bytes ), mediaType, null );
}

/**
* Creates an attachment from a binary input stream.
* The content of the stream will be transformed into a Base64 encoded string
* @throws IOException if an I/O error occurs
* @throws java.lang.IllegalArgumentException if mediaType is not binary
*/
public static Attachment fromBinaryInputStream( InputStream inputStream, MediaType mediaType ) throws IOException {
return fromBinaryBytes( ByteStreams.toByteArray( inputStream ), mediaType );
}

/**
* Creates an attachment from the given binary file {@code file}.
* The content of the file will be transformed into a Base64 encoded string.
* @throws IOException if an I/O error occurs
* @throws java.lang.IllegalArgumentException if mediaType is not binary
*/
public static Attachment fromBinaryFile( File file, MediaType mediaType ) throws IOException {
FileInputStream stream = new FileInputStream( file );
try {
return fromBinaryInputStream( stream, mediaType );
} finally {
ResourceUtil.close( stream );
}
}

/**
* Creates a non-binary attachment from the given file.
* @throws IOException if an I/O error occurs
* @throws java.lang.IllegalArgumentException if mediaType is binary
*/
public static Attachment fromTextFile( File file, MediaType mediaType, Charset charSet ) throws IOException {
return fromText( Files.toString( file, charSet ), mediaType );
}

/**
* Creates a non-binary attachment from the given file.
* @throws IOException if an I/O error occurs
* @throws java.lang.IllegalArgumentException if mediaType is binary
*/
public static Attachment fromTextInputStream( InputStream inputStream, MediaType mediaType, Charset charset ) throws IOException {
return fromText( CharStreams.toString( new InputStreamReader( inputStream, charset ) ), mediaType );
}

/**
* Equivalent to {@link com.tngtech.jgiven.attachment.Attachment#Attachment(String, MediaType)}
* @throws java.lang.IllegalArgumentException if mediaType is binary
*/
public static Attachment fromText( String content, MediaType mediaType ) {
if( mediaType.isBinary() ) {
throw new IllegalArgumentException( "MediaType must not be binary" );
}
return new Attachment( content, mediaType );
}

/**
* Equivalent to {@link com.tngtech.jgiven.attachment.Attachment#Attachment(String, MediaType)}
* @throws java.lang.IllegalArgumentException if mediaType is not binary
*/
public static Attachment fromBase64( String base64encodedContent, MediaType mediaType ) {
if( !mediaType.isBinary() ) {
throw new IllegalArgumentException( "MediaType must be binary" );
}
return new Attachment( base64encodedContent, mediaType );
}

String getMimeType();
}

This file was deleted.

118 changes: 118 additions & 0 deletions jgiven-core/src/main/java/com/tngtech/jgiven/attachment/MediaType.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,118 @@
package com.tngtech.jgiven.attachment;

import static com.tngtech.jgiven.attachment.MediaType.Type.*;

/**
* Represents a <a href="http://www.iana.org/assignments/media-types/media-types.xhtml">Media Type</a>.
*/
public class MediaType {

/**
* Represents the type of a Media Type
*/
public static enum Type {
APPLICATION( "application" ),
AUDIO( "audio" ),
IMAGE( "image" ),
TEXT( "text" ),
VIDEO( "video" );

private final String value;

Type( String value ) {
this.value = value;
}

@Override
public String toString() {
return value;
}

/**
* Get the type from a given string
*/
public Type fromString( String string ) {
for( Type type : values() ) {
if( type.value.equalsIgnoreCase( string ) ) {
return type;
}
}
throw new IllegalArgumentException( "Unknown type " + string );
}

}

public static final MediaType PNG = image( "png" );
public static final MediaType PLAIN_TEXT = text( "plain" );

private final Type type;
private final String subType;
private final boolean binary;

/**
* Creates a new MediaType
* @param type the type
* @param subType the subtype
* @param binary whether or not content of this media type is binary. If {@code true}, the
* content will be encoded as Base64 when stored in the JSON model.
*/
public MediaType( Type type, String subType, boolean binary ) {
this.type = type;
this.subType = subType;
this.binary = binary;
}

/**
* The type of the Media Type.
*/
public Type getType() {
return type;
}

/**
* The subtype of the Media Type.
*/
public String getSubType() {
return subType;
}

/**
* Whether this media type is binary or not.
*/
public boolean isBinary() {
return binary;
}

public String asString() {
return type.value + "/" + subType;
}

/**
* Creates a binary image media type with the given subtype.
*/
public static MediaType image( String subType ) {
return new MediaType( IMAGE, subType, true );
}

/**
* Creates a binary video media type with the given subtype.
*/
public static MediaType video( String subType ) {
return new MediaType( VIDEO, subType, true );
}

/**
* Creates a binary audio media type with the given subtype.
*/
public static MediaType audio( String subType ) {
return new MediaType( AUDIO, subType, true );
}

/**
* Creates a non-binary text media type with the given subtype.
*/
public static MediaType text( String subType ) {
return new MediaType( TEXT, subType, false );
}

}
Loading

0 comments on commit 05b531e

Please sign in to comment.