Changeset 5651


Ignore:
Timestamp:
Jun 8, 2011, 3:00:33 PM (10 years ago)
Author:
Nicklas Nordborg
Message:

References #1597: Subtypes of items

Implemented more functionality for the item overview that is related to item subtypes.

  • Validation of project default subtypes.
  • Validation of related subtypes between items. For example, if we have a sample with subtype S that has a related protocol subtype P then the protocol attached to the sample should use the P subtype (if not an INCORRECT_PROTOCOLTYPE warning is generated). On the other hand, if the sample subtype doesn't have a related protocol subtype, warnings about missing items are not generated.
  • Display subtype information in the overview.


There are still a few labeled extract/hybridization validation rules that have not been fixed.

Location:
trunk
Files:
3 added
36 edited
2 moved

Legend:

Unmodified
Added
Removed
  • trunk/src/core/net/sf/basedb/core/Hardware.java

    r5642 r5651  
    9898  public static final int MAX_VERSIONSTRING_LENGTH = HardwareData.MAX_VERSIONSTRING_LENGTH;
    9999
     100  /**
     101    Get the system id for the hardware subtype that should be used on an item
     102    that doesn't have a subtype. This includes {@link Subtypable} items with a
     103    null {@link ItemSubtype} and all other non-subtypable items which can be
     104    linked to a hardware.
     105    @param itemType The item type
     106    @return The system id of the default hardware type or null
     107    @since 3.0
     108  */
     109  public static String getDefaultSystemId(Item itemType)
     110  {
     111    String defaultId = null;
     112    if (itemType == Item.ARRAYBATCH)
     113    {
     114      defaultId = PRINT_ROBOT;
     115    }
     116    else if (itemType == Item.SCAN)
     117    {
     118      defaultId = SCANNER;
     119    }
     120    return defaultId;
     121  }
     122
     123 
    100124  /**
    101125    Create a new <code>Hardware</code> item.
  • trunk/src/core/net/sf/basedb/core/ItemSubtype.java

    r5647 r5651  
    111111 
    112112  /**
     113    Same as {@link #getRelatedSubtype(DbControl, Subtypable, Item, int, int)} with the
     114    same id for the last two parameters.
     115  */
     116  public static ItemSubtype getRelatedSubtype(DbControl dc, Subtypable item, Item relatedItem, int defaultSubtype)
     117  {
     118    return getRelatedSubtype(dc, item, relatedItem, defaultSubtype, defaultSubtype);
     119  }
     120 
     121  /**
    113122    Utility method for loading a subtype that is related to the subtype of the given item.
    114123    @param dc A DbControl to use for database access
    115124    @param item A subtypable item
    116125    @param relatedItem The main item type of the related subtype we are looking for
    117     @param defaultRelatedId An ID of the subtype to return if no related subtype is found
    118      
     126    @param defaultIfNoSubtype The ID of the subtype to return if the item has no
     127      subtype
     128    @param defaultIfNoRelated The ID of the subtype to return if the item has a subtype,
     129      but the subtype has no related subtype for the given related item type
    119130    @return An ItemSubtype or null
    120131  */
    121   public static ItemSubtype getRelatedSubtype(DbControl dc, Subtypable item, Item relatedItem, int defaultRelatedId)
     132  public static ItemSubtype getRelatedSubtype(DbControl dc, Subtypable item, Item relatedItem,
     133    int defaultIfNoSubtype, int defaultIfNoRelated)
    122134  {
    123135    ItemSubtype related = null;
     
    126138    {
    127139      related = subtype.getRelatedSubtype(relatedItem);
    128     }
    129     if (related == null && defaultRelatedId > 0)
    130     {
    131       related = getById(dc, defaultRelatedId);
     140      if (related == null && defaultIfNoRelated != 0)
     141      {
     142        related = getById(dc, defaultIfNoRelated);
     143      }
     144    }
     145    else if (defaultIfNoSubtype != 0)
     146    {
     147      related = getById(dc, defaultIfNoSubtype);
    132148    }
    133149    return related;
     150  }
     151 
     152  /**
     153    Utility method for locating a subtype that is related to the subtype of
     154    a given item. This method will check each item type in turn and return
     155    the first subtype that is found.
     156   
     157    @param dc A DbControl to use for database access
     158    @param item A subtypable item
     159    @param relatedItems The main item type of the related subtype we are looking for
     160    @return An ItemSubtype or null
     161  */
     162  public static ItemSubtype getRelatedSubtype(DbControl dc, Subtypable item, Item... relatedItems)
     163  {
     164    ItemSubtype subtype = item.getItemSubtype();
     165    if (subtype == null) return null;
     166   
     167    for (Item itemType : relatedItems)
     168    {
     169      ItemSubtype related = subtype.getRelatedSubtype(itemType);
     170      if (related != null) return related;
     171    }
     172   
     173    return null;
    134174  }
    135175 
  • trunk/src/core/net/sf/basedb/core/Protocol.java

    r5642 r5651  
    133133  public static final int MAX_EXTERNAL_ID_LENGTH = ProtocolData.MAX_EXTERNAL_ID_LENGTH;
    134134
     135  /**
     136    Get the system id for the protocol subtype that should be used on an item
     137    that doesn't have a subtype. This includes {@link Subtypable} items with a
     138    null {@link ItemSubtype} and all other non-subtypable items which can be
     139    linked to a protocol.
     140    @param itemType The item type
     141    @return The system id of the default protocol or null
     142    @since 3.0
     143  */
     144  public static String getDefaultSystemId(Item itemType)
     145  {
     146    String defaultId = null;
     147    if (itemType == Item.SAMPLE)
     148    {
     149      defaultId = SAMPLING;
     150    }
     151    else if (itemType == Item.EXTRACT)
     152    {
     153      defaultId = EXTRACTION;
     154    }
     155    else if (itemType == Item.ARRAYBATCH)
     156    {
     157      defaultId = PRINTING;
     158    }
     159    else if (itemType == Item.SCAN)
     160    {
     161      defaultId = SCANNING;
     162    }
     163    else if (itemType == Item.RAWBIOASSAY)
     164    {
     165      defaultId = FEATURE_EXTRACTION;
     166    }
     167    return defaultId;
     168  }
    135169 
    136170  /**
  • trunk/src/core/net/sf/basedb/core/Software.java

    r5630 r5651  
    6565  */
    6666  public static final int MAX_VERSIONSTRING_LENGTH = SoftwareData.MAX_VERSIONSTRING_LENGTH;
     67 
     68  /**
     69    Get the system id for the software subtype that should be used on an item
     70    that doesn't have a subtype. This includes {@link Subtypable} items with a
     71    null {@link ItemSubtype} and all other non-subtypable items which can be
     72    linked to a software.
     73    @param itemType The item type
     74    @return The system id of the default software type or null
     75    @since 3.0
     76  */
     77  public static String getDefaultSystemId(Item itemType)
     78  {
     79    String defaultId = null;
     80    if (itemType == Item.RAWBIOASSAY)
     81    {
     82      defaultId = FEATURE_EXTRACTION;
     83    }
     84    return defaultId;
     85  }
     86
     87 
    6788  /**
    6889    Create a new <code>Software</code> item.
  • trunk/src/core/net/sf/basedb/util/overview/OverviewUtil.java

    r5650 r5651  
    8888          {
    8989            Validator.MISSING_BIOSOURCE, Validator.MISSING_SAMPLE, Validator.MISSING_EXTRACT,
    90             Validator.MISSING_LABELED_EXTRACT, Validator.MISSING_HYBRIDIZATION,
     90            Validator.MISSING_BIOASSAY,
    9191            Validator.MISSING_SCAN, Validator.MISSING_ARRAYDESIGN, Validator.MISSING_PROTOCOL,
    92             Validator.MISSING_HARDWARE, Validator.MISSING_SOFTWARE,
     92            Validator.MISSING_HARDWARE, Validator.MISSING_SOFTWARE, Validator.MISSING_TAG,
    9393            Validator.MISSING_ARRAYSLIDE, Validator.MISSING_ARRAYBATCH, Validator.MISSING_ANYTOANY
     94          })
     95        );
     96      temp.put("Subtypes",
     97          Arrays.asList(new Validator[]
     98          {
     99            Validator.INCORRECT_BIOSOURCE_TYPE, Validator.INCORRECT_SAMPLE_TYPE,
     100            Validator.INCORRECT_EXTRACT_TYPE, Validator.INCORRECT_PROTOCOLTYPE,
     101            Validator.INCORRECT_HARDWARETYPE, Validator.INCORRECT_SOFTWARETYPE,
     102            Validator.INCORRECT_TAGTYPE
    94103          })
    95104        );
     
    120129           {
    121130            Validator.DENIED_BIOSOURCE, Validator.DENIED_SAMPLE, Validator.DENIED_EXTRACT,
    122             Validator.DENIED_LABEL, Validator.DENIED_HYBRIDIZATION, Validator.DENIED_SCAN,
     131            Validator.DENIED_TAG, Validator.DENIED_BIOASSAY, Validator.DENIED_SCAN,
    123132            Validator.DENIED_ARRAYDESIGN, Validator.DENIED_PLATFORM, Validator.DENIED_PROTOCOL, Validator.DENIED_HARDWARE,
    124133            Validator.DENIED_SOFTWARE, Validator.DENIED_ARRAYSLIDE, Validator.DENIED_ARRAYBATCH,
     
    131140          {
    132141            Validator.NONMATHCING_ARRAYDESIGN, Validator.NONMATCHING_SPOTCOUNT,
    133             Validator.MULTIPLE_ARRAYDESIGNS,
    134             Validator.INCORRECT_PROTOCOLTYPE, Validator.INCORRECT_SOFTWARETYPE,
    135             Validator.INCORRECT_HARDWARETYPE, Validator.INCORRECT_ARRAY_NUM,
     142            Validator.MULTIPLE_ARRAYDESIGNS, Validator.INCORRECT_ARRAY_NUM,
    136143            Validator.DUPLICATE_ARRAY_NUM, Validator.INCORRECT_NUM_LABELEDEXTRACTS,
    137144            Validator.NONUNIQUE_LABEL, Validator.DIFFERENT_LABEL,
  • trunk/src/core/net/sf/basedb/util/overview/Validator.java

    r5518 r5651  
    150150
    151151  /**
    152     Validator rule that checks for missing hybridization. Default severity level
    153     is WARNING.
    154   */
    155   public static final Validator MISSING_HYBRIDIZATION = new Validator(
    156       "missing.hybridization", "Missing hybridization",
    157       "Checks if a hybridization has been specified for a scan or array slide",
    158       "Missing hybridization", Severity.WARNING
    159     );
    160 
    161   /**
    162     Validator rule that checks for denied access to hybridization. Default severity level
    163     is WARNING.
    164   */
    165   public static final Validator DENIED_HYBRIDIZATION = new Validator(
    166       "denied.hybridization", "Access denied to hybridization",
    167       "Checks if the user is denied access to a hybridization",
    168       "Access denied to hybridization", Severity.WARNING
     152    Validator rule that checks for missing physical bioassay. Default severity level
     153    is WARNING.
     154  */
     155  public static final Validator MISSING_BIOASSAY = new Validator(
     156      "missing.bioassay", "Missing bioassay",
     157      "Checks if a physical bioassay has been specified for a scan or array slide",
     158      "Missing bioassay", Severity.WARNING
     159    );
     160
     161  /**
     162    Validator rule that checks for denied access to physical bioassay. Default severity level
     163    is WARNING.
     164  */
     165  public static final Validator DENIED_BIOASSAY = new Validator(
     166      "denied.bioassay", "Access denied to bioassay",
     167      "Checks if the user is denied access to a physical bioassay",
     168      "Access denied to bioassay", Severity.WARNING
    169169    );
    170170
     
    175175  public static final Validator MISSING_ARRAYSLIDE = new Validator(
    176176      "missing.slide", "Missing array slide",
    177       "Checks if an array slide has been specified for a hybiridzation",
     177      "Checks if an array slide has been specified for a physical bioassay",
    178178      "Missing array slide", Severity.WARNING
    179179    );
     
    190190
    191191  /**
    192     Validator rule that checks for missing labeled extract. Default severity level
    193     is WARNING.
    194   */
    195   public static final Validator MISSING_LABELED_EXTRACT = new Validator(
    196       "missing.labeledextract", "Missing labeled extract",
    197       "Checks if at least one labeled extract has been specified as parent to a " +
    198       "pooled labeled extract or a hybridization",
    199       "Missing labeled extract", Severity.WARNING
    200     );
    201  
    202   /**
    203192    Validator rule that checks for missing extract. Default severity level
    204193    is WARNING.
     
    262251    );
    263252
    264   /**
    265     Validator rule that checks for denied access to labels. Default severity level
    266     is WARNING.
    267   */
    268   public static final Validator DENIED_LABEL = new Validator(
    269       "denied.label", "Access denied to label",
    270       "Checks if the user is denied access to a label",
    271       "Access denied to label", Severity.WARNING
     253 
     254  /**
     255    Validator rule that checks for missing tag. Default severity level
     256    is WARNING.
     257  */
     258  public static final Validator MISSING_TAG = new Validator(
     259      "missing.tag", "Missing tag",
     260      "Checks if a tag has been specified for an extract",
     261      "Missing tag", Severity.WARNING
     262    );
     263 
     264  /**
     265    Validator rule that checks for denied access to tags. Default severity level
     266    is WARNING.
     267    @since 3.0
     268  */
     269  public static final Validator DENIED_TAG = new Validator(
     270      "denied.tag", "Access denied to tag",
     271      "Checks if the user is denied access to a tag.",
     272      "Access denied to tag", Severity.WARNING
    272273    );
    273274 
     
    478479
    479480  /**
     481    Validator rule that checks if the tag attached to an extract
     482    has a correct subtype. Default severity level is WARNING.
     483    @since 3.0
     484  */
     485  public static final Validator INCORRECT_TAGTYPE = new Validator(
     486      "subtype.tag", "Incorrect tag subtype",
     487      "Checks if the tag attached to an extract has a correct subtype.",
     488      "Incorrect tag subtype", Severity.WARNING
     489    );
     490
     491 
     492  /**
    480493    Validator rule that checks if the protocol attached to an item
    481494    has a correct protocol type. Default severity level is WARNING.
    482495  */
    483496  public static final Validator INCORRECT_PROTOCOLTYPE = new Validator(
    484       "misc.incorrectprotocoltype", "Incorrect protocol type",
     497      "subtype.protocol", "Incorrect protocol subtype",
    485498      "Checks if the protocol attached to an item has a correct protocol type.",
    486       "Incorrect protocol type", Severity.WARNING
     499      "Incorrect protocol subtype", Severity.WARNING
    487500    );
    488501
     
    492505  */
    493506  public static final Validator INCORRECT_SOFTWARETYPE = new Validator(
    494       "misc.incorrectsoftwaretype", "Incorrect software type",
     507      "subtype.software", "Incorrect software subtype",
    495508      "Checks if the software attached to an item has a correct software type.",
    496       "Incorrect software type", Severity.WARNING
     509      "Incorrect software subtype", Severity.WARNING
    497510    );
    498511
     
    502515  */
    503516  public static final Validator INCORRECT_HARDWARETYPE = new Validator(
    504       "misc.incorrecthardwaretype", "Incorrect hardware type",
     517      "subtype.hardware", "Incorrect hardware subtype",
    505518      "Checks if the hardware attached to an item has a correct hardware type.",
    506       "Incorrect hardware type", Severity.WARNING
    507     );
     519      "Incorrect hardware subtype", Severity.WARNING
     520    );
     521 
     522  /**
     523    Validator that checks if the parent biosource of a sample
     524    has the expected subtype. Default severity level is WARNING.
     525    @since 3.0
     526   */
     527  public static final Validator INCORRECT_BIOSOURCE_TYPE = new Validator(
     528      "subtype.biosource", "Incorrect biosource subtype",
     529      "Checks if the parent biosource of a sample has the expected subtype.",
     530      "Incorrect biosource subtype", Severity.WARNING
     531  );
     532
     533  /**
     534    Validator that checks if the parent sample of a sample/extract
     535    has the expected subtype. Default severity level is WARNING.
     536    @since 3.0
     537   */
     538  public static final Validator INCORRECT_SAMPLE_TYPE = new Validator(
     539      "subtype.sample", "Incorrect sample subtype",
     540      "Checks if the parent sample of a sample/extract has the expected subtype.",
     541      "Incorrect sample subtype", Severity.WARNING
     542  );
     543
     544  /**
     545    Validator that checks if the parent extract of a extract/bioassay
     546    has the expected subtype. Default severity level is WARNING.
     547    @since 3.0
     548   */
     549  public static final Validator INCORRECT_EXTRACT_TYPE = new Validator(
     550      "subtype.extract", "Incorrect extract subtype",
     551      "Checks if the parent extract of an extract/physical bioassay has the expected subtype.",
     552      "Incorrect extract subtype", Severity.WARNING
     553  );
    508554 
    509555  /**
  • trunk/src/core/net/sf/basedb/util/overview/loader/ArraySlideLoader.java

    r5642 r5651  
    129129  /**
    130130    Loads the physical bioassay node that is related to the given array slide node.
    131     @see HybridizationLoader#createForwardNode(DbControl, OverviewContext, Node)
     131    @see PhysicalBioAssayLoader#createForwardNode(DbControl, OverviewContext, Node)
    132132  */
    133133  @Override
  • trunk/src/core/net/sf/basedb/util/overview/loader/BasicItemNodeLoaderFactory.java

    r5642 r5651  
    221221    registerCheckedNodeLoader(Item.ARRAYBATCH, ArrayBatchLoader.class);
    222222    registerCheckedNodeLoader(Item.ARRAYSLIDE, ArraySlideLoader.class);
    223     registerCheckedNodeLoader(Item.PHYSICALBIOASSAY, HybridizationLoader.class);
     223    registerCheckedNodeLoader(Item.PHYSICALBIOASSAY, PhysicalBioAssayLoader.class);
    224224    registerCheckedNodeLoader(Item.SCAN, ScanLoader.class);
    225225    registerCheckedNodeLoader(Item.RAWBIOASSAY, RawBioAssayLoader.class);
     
    228228    // Property node loaders
    229229    registerCheckedNodeLoader(Item.PROTOCOL, ProtocolLoader.class);
     230    registerCheckedNodeLoader(Item.TAG, TagLoader.class);
    230231    registerCheckedNodeLoader("PROTOCOL.PARAMETER", ProtocolParameterLoader.class);
    231232    registerCheckedNodeLoader("EXPERIMENTAL.FACTOR", ExperimentalFactorLoader.class);
  • trunk/src/core/net/sf/basedb/util/overview/loader/ExtractLoader.java

    r5642 r5651  
    3636import net.sf.basedb.util.overview.filter.ItemTypeFilter;
    3737import net.sf.basedb.util.overview.node.ChildNodeDirection;
    38 import net.sf.basedb.util.overview.node.NameableNameGenerator;
     38import net.sf.basedb.util.overview.node.ExtractNameGenerator;
    3939import net.sf.basedb.util.overview.Node;
    4040import net.sf.basedb.util.overview.node.NodeFactory;
     
    5757  {
    5858    super(Item.EXTRACT, ALLOW_ROOT_NODE,
    59         new NameableNameGenerator<Extract>("extract", "Extract"));
     59        new ExtractNameGenerator("extract", "Extract"));
    6060  }
    6161 
     
    118118    <li>Annotations: {@link AnnotationLoader#createPropertyNode(DbControl, OverviewContext, Node)}
    119119    <li>Protocol: {@link ProtocolLoader#createPropertyNode(DbControl, OverviewContext, Node)}
     120    <li>Hardware: {@link HardwareLoader#createPropertyNode(DbControl, OverviewContext, Node)}
    120121    </ul>
    121122  */
     
    124125  {
    125126    getNodeLoader(context, Item.ANNOTATION).createPropertyNode(dc, context, extractNode);
     127    getNodeLoader(context, Item.TAG).createPropertyNode(dc, context, extractNode);
    126128    getNodeLoader(context, Item.PROTOCOL).createPropertyNode(dc, context, extractNode);
     129    getNodeLoader(context, Item.HARDWARE).createPropertyNode(dc, context, extractNode);
    127130    getNodeLoader(context, Item.ANYTOANY).createPropertyNode(dc, context, extractNode);
    128131  }
     
    132135    this extract.
    133136    @see ExtractLoader#createForwardNode(DbControl, OverviewContext, Node)
    134     @see HybridizationLoader#createForwardNode(DbControl, OverviewContext, Node)
     137    @see PhysicalBioAssayLoader#createForwardNode(DbControl, OverviewContext, Node)
    135138  */
    136139  @Override
     
    226229      if (folderNode == null)
    227230      {
    228         folderNode = new Node("labeledextracts", "Labeled extracts", parentNode, ChildNodeDirection.REVERSE);
     231        folderNode = new Node("extracts", "Extracts", parentNode, ChildNodeDirection.REVERSE);
    229232      }
    230233      createItemNode(nf, extract, extract, false, folderNode, ChildNodeDirection.REVERSE);
     
    233236    return folderNode;
    234237  }
    235 
    236  
    237   /**
    238     Create a reverse-loading extract node from a labeled extract. Eg. the child node
    239     is the extract that is the parent of the (non-pooled) labeled extract.
    240   */
    241   /*
    242   private Node createReverseNode(LabeledExtract labeledExtract, DbControl dc, OverviewContext context, Node parentNode)
    243   {
    244     NodeFactory<Extract> nf = getNodeFactory(dc, context);
    245     Extract extract = null;
    246     boolean denied = false;
    247     try
    248     {
    249       extract = labeledExtract.getExtract();
    250     }
    251     catch (PermissionDeniedException ex)
    252     {
    253       denied = true;
    254     }
    255     Node extractNode = createItemNode(nf, extract, extract, denied,
    256         parentNode, ChildNodeDirection.REVERSE);
    257     return extractNode;
    258   }
    259   */
    260238
    261239  /**
  • trunk/src/core/net/sf/basedb/util/overview/loader/HardwareLoader.java

    r5642 r5651  
    2626import net.sf.basedb.core.DbControl;
    2727import net.sf.basedb.core.Hardware;
     28import net.sf.basedb.core.MeasuredBioMaterial;
    2829import net.sf.basedb.core.PhysicalBioAssay;
    2930import net.sf.basedb.core.Item;
     
    7374    Hardware hardware = null;
    7475    boolean denied = false;
    75     String nodeTitlePrefix = "Hardware";
    7676    try
    7777    {
     
    7979      if (parentItem instanceof Scan)
    8080      {
    81         nodeTitlePrefix = "Scanner";
    8281        hardware = ((Scan)parentItem).getScanner();
    8382      }
    8483      else if (parentItem instanceof PhysicalBioAssay)
    8584      {
    86         nodeTitlePrefix = "Hyb. station";
    8785        hardware = ((PhysicalBioAssay)parentItem).getCreationEvent().getHardware();
     86      }
     87      else if (parentItem instanceof MeasuredBioMaterial)
     88      {
     89        hardware = ((MeasuredBioMaterial)parentItem).getCreationEvent().getHardware();
    8890      }
    8991      else if (parentItem instanceof ArrayBatch)
    9092      {
    91         nodeTitlePrefix = "Print robot";
    9293        hardware = ((ArrayBatch)parentItem).getPrintRobot();
    9394      }
     
    100101    }
    101102   
    102     NodeFactory<Hardware> nf = getNodeFactory(dc, context,
    103       getNodeValidator(context), new NameableNameGenerator<Hardware>("hardware", nodeTitlePrefix));
     103    NodeFactory<Hardware> nf = getNodeFactory(dc, context);
    104104    Node hardwareNode = createItemNode(nf, hardware, hardware, denied,
    105105        parentNode, ChildNodeDirection.NONE);
  • trunk/src/core/net/sf/basedb/util/overview/loader/PhysicalBioAssayLoader.java

    r5642 r5651  
    4141
    4242/**
    43   Node loader implementation for hybridizations. There are two forward-loading
     43  Node loader implementation for physical bioassays. There are two forward-loading
    4444  directions:
    4545  <ol>
    46   <li>{@link LabeledExtract}:s -&gt; {@link PhysicalBioAssay}:s -&gt;
     46  <li>{@link Extract}:s -&gt; {@link PhysicalBioAssay}:s -&gt;
    4747  {@link Scan}:s.
    4848  <li>{@link ArraySlide}:s -&gt; {@link PhysicalBioAssay}:s -&gt;
     
    5151 
    5252  The reverse-loading direction starts with a scan and moves to both
    53   labeled extracts and array slide.
     53  extracts and array slide.
    5454
    5555  @author Nicklas
     
    5757  @base.modified $Date$
    5858*/
    59 public class HybridizationLoader
     59public class PhysicalBioAssayLoader
    6060  extends BasicItemNodeLoader<PhysicalBioAssay>
    6161{
    62   public HybridizationLoader()
     62  public PhysicalBioAssayLoader()
    6363  {
    6464    super(Item.PHYSICALBIOASSAY, ALLOW_ROOT_NODE,
    65         new NameableNameGenerator<PhysicalBioAssay>("hybridization", "Hybridization"));
     65        new NameableNameGenerator<PhysicalBioAssay>("bioassay", "Physical bioassay"));
    6666  }
    6767
     
    7171  */
    7272  /**
    73     Create forward-loading hybridization nodes from either a labeled extract or
     73    Create forward-loading hybridization nodes from either an extract or
    7474    an array slide node. The returned node is either folder-type node containing
    75     nodes for each hybridization that has been created from the labeled extract
    76     or an item node with the hybridization on the array slide.
    77     @return The folder node with the hybridizations, or the item node (can be null)
     75    nodes for each bioassay that has been created from the extract
     76    or an item node with the bioassay on the array slide.
     77    @return The folder node with the bioassays, or the item node (can be null)
    7878  */
    7979  @Override
     
    9494 
    9595  /**
    96     Create a reverse-loading hybridization node from the scan node.
    97     @return A hybridization node, or null if the scan doesn't have a
     96    Create a reverse-loading bioassay node from the scan node.
     97    @return A bioassay node, or null if the scan doesn't have a
    9898      hybridization
    9999  */
     
    102102  {
    103103    NodeFactory<PhysicalBioAssay> nf = getNodeFactory(dc, context);
    104     PhysicalBioAssay hyb = null;
     104    PhysicalBioAssay bioAssay = null;
    105105    boolean denied = false;
    106106    int arrayNum = 0;
     
    108108    {
    109109      Scan scan = (Scan)scanNode.getItem(dc);
    110       hyb = scan.getHybridization();
     110      bioAssay = scan.getHybridization();
    111111      Node rbaNode = scanNode.getFirstParent(new ItemTypeFilter(Item.RAWBIOASSAY));
    112112      if (rbaNode != null)
     
    120120      denied = true;
    121121    }
    122     Object cacheKey = new IndexedCacheKey(hyb, arrayNum);
    123     Node hybNode = createItemNode(nf, hyb, cacheKey, denied, scanNode, ChildNodeDirection.REVERSE);
    124     return hybNode;
     122    Object cacheKey = new IndexedCacheKey(bioAssay, arrayNum);
     123    Node bioAssayNode = createItemNode(nf, bioAssay, cacheKey, denied, scanNode, ChildNodeDirection.REVERSE);
     124    return bioAssayNode;
    125125  }
    126126  // --------------------------------------
     
    130130  */
    131131  /**
    132     Loads property nodes of a hybridization.
     132    Loads property nodes of a physical bioassay.
    133133    <ul>
    134134    <li>Annotations: {@link AnnotationLoader#createPropertyNode(DbControl, OverviewContext, Node)}
    135135    <li>Protocol: {@link ProtocolLoader#createPropertyNode(DbControl, OverviewContext, Node)}
    136     <li>Hyb. station: {@link HardwareLoader#createPropertyNode(DbControl, OverviewContext, Node)}
     136    <li>Hardware: {@link HardwareLoader#createPropertyNode(DbControl, OverviewContext, Node)}
    137137    </ul>
    138138  */
    139139  @Override
    140   protected void loadPropertyChildNodes(DbControl dc, OverviewContext context, Node hybNode)
    141   {
    142     getNodeLoader(context, Item.ANNOTATIONTYPE).createPropertyNode(dc, context, hybNode);
    143     getNodeLoader(context, Item.PROTOCOL).createPropertyNode(dc, context, hybNode);
    144     getNodeLoader(context, Item.HARDWARE).createPropertyNode(dc, context, hybNode);
    145     getNodeLoader(context, Item.ANYTOANY).createPropertyNode(dc, context, hybNode);
     140  protected void loadPropertyChildNodes(DbControl dc, OverviewContext context, Node bioAssayNode)
     141  {
     142    getNodeLoader(context, Item.ANNOTATIONTYPE).createPropertyNode(dc, context, bioAssayNode);
     143    getNodeLoader(context, Item.PROTOCOL).createPropertyNode(dc, context, bioAssayNode);
     144    getNodeLoader(context, Item.HARDWARE).createPropertyNode(dc, context, bioAssayNode);
     145    getNodeLoader(context, Item.ANYTOANY).createPropertyNode(dc, context, bioAssayNode);
    146146  }
    147147 
     
    150150    <ul>
    151151    <li>Scans: {@link ScanLoader#createForwardNode(DbControl, OverviewContext, Node)}
    152     <li>Array slide in reverse direction (if the parent node is a labeled extract):
     152    <li>Array slide in reverse direction (if the parent node is an extract):
    153153      {@link ArraySlideLoader#createReverseNode(DbControl, OverviewContext, Node)}
    154     <li>Labeled extracts in reverse direction (if the parent node is the array slide):
    155       {@link LabeledExtractLoader#createReverseNode(DbControl, OverviewContext, Node)}
     154    <li>Extracts in reverse direction (if the parent node is the array slide):
     155      {@link ExtractLoader#createReverseNode(DbControl, OverviewContext, Node)}
    156156    </ul>
    157157  */
    158158  @Override
    159   protected void loadForwardChildNodes(DbControl dc, OverviewContext context, Node hybNode)
    160   {
    161     getNodeLoader(context, Item.SCAN).createForwardNode(dc, context, hybNode);
    162     Node parent = hybNode.getParent();
     159  protected void loadForwardChildNodes(DbControl dc, OverviewContext context, Node bioAssayNode)
     160  {
     161    getNodeLoader(context, Item.SCAN).createForwardNode(dc, context, bioAssayNode);
     162    Node parent = bioAssayNode.getParent();
    163163    if (parent != null && parent.getNodeType() == Node.Type.FOLDER)
    164164    {
     
    168168    if (parentItemType == Item.EXTRACT)
    169169    {
    170       getNodeLoader(context, Item.ARRAYSLIDE).createReverseNode(dc, context, hybNode);
     170      getNodeLoader(context, Item.ARRAYSLIDE).createReverseNode(dc, context, bioAssayNode);
    171171    }
    172172    if (parentItemType == Item.ARRAYSLIDE)
    173173    {
    174       getNodeLoader(context, Item.EXTRACT).createReverseNode(dc, context, hybNode);
     174      getNodeLoader(context, Item.EXTRACT).createReverseNode(dc, context, bioAssayNode);
    175175    }
    176176  }
     
    179179    Load reverse child nodes:
    180180    <ul>
    181     <li>Labeled extracts: {@link LabeledExtractLoader#createReverseNode(DbControl, OverviewContext, Node)}
     181    <li>Extracts: {@link ExtractLoader#createReverseNode(DbControl, OverviewContext, Node)}
    182182    <li>Array slide: {@link ArraySlideLoader#createReverseNode(DbControl, OverviewContext, Node)}
    183183    </ul>
     
    192192 
    193193  /**
    194     Create forward-loading hybridization nodes for the hybridizations
    195     that has a given labeled extract as a source.
     194    Create forward-loading bioassay nodes for the bioassays
     195    that has a given extract as a source.
    196196  */
    197197  private Node createForwardNode(Extract extract, DbControl dc, OverviewContext context, Node parentNode)
     
    203203    while (it.hasNext())
    204204    {
    205       PhysicalBioAssay hyb = it.next();
    206       int arrayNum = hyb.getCreationEvent().getSourceGroup(extract);
    207       Object cacheKey = arrayNum == 0 ? hyb : new IndexedCacheKey(hyb, arrayNum);
     205      PhysicalBioAssay bioAssay = it.next();
     206      int arrayNum = bioAssay.getCreationEvent().getSourceGroup(extract);
     207      Object cacheKey = arrayNum == 0 ? bioAssay : new IndexedCacheKey(bioAssay, arrayNum);
    208208      if (folderNode == null)
    209209      {
    210         folderNode = new Node("hybridizations", "Hybridizations", parentNode, ChildNodeDirection.FORWARD);
     210        folderNode = new Node("bioassays", "Physical bioassays", parentNode, ChildNodeDirection.FORWARD);
    211211      }
    212       createItemNode(nf, hyb, cacheKey, false, folderNode, ChildNodeDirection.FORWARD);
     212      createItemNode(nf, bioAssay, cacheKey, false, folderNode, ChildNodeDirection.FORWARD);
    213213    }
    214214    postValidateFolder(nf, folderNode, parentNode, false);
     
    217217
    218218  /**
    219     Create a forward-loading hybridization node from an array slide.
     219    Create a forward-loading bioassay node from an array slide.
    220220  */
    221221  private Node createForwardNode(ArraySlide slide, DbControl dc, OverviewContext context, Node parentNode)
    222222  {
    223223    NodeFactory<PhysicalBioAssay> nf = getNodeFactory(dc, context);
    224     PhysicalBioAssay hyb = null;
     224    PhysicalBioAssay bioAssay = null;
    225225    boolean denied = false;
    226226    try
    227227    {
    228       hyb = slide.getPhysicalBioAssay();
     228      bioAssay = slide.getPhysicalBioAssay();
    229229    }
    230230    catch (PermissionDeniedException ex)
     
    232232      denied = true;
    233233    }
    234     Node hybNode = createItemNode(nf, hyb, hyb, denied, parentNode, ChildNodeDirection.FORWARD);
     234    Node hybNode = createItemNode(nf, bioAssay, bioAssay, denied, parentNode, ChildNodeDirection.FORWARD);
    235235    return hybNode;
    236236  }
  • trunk/src/core/net/sf/basedb/util/overview/loader/ScanLoader.java

    r5642 r5651  
    165165  /**
    166166    Loads the physical bioassay node that is the parent of this scan.
    167     @see HybridizationLoader#createReverseNode(DbControl, OverviewContext, Node)
     167    @see PhysicalBioAssayLoader#createReverseNode(DbControl, OverviewContext, Node)
    168168  */
    169169  @Override
  • trunk/src/core/net/sf/basedb/util/overview/node/NameableNameGenerator.java

    r4749 r5651  
    5959  }
    6060 
    61 
    6261  @Override
    6362  public String getNodeName(I item, Node parentNode)
     
    7574  {
    7675    StringBuilder title = new StringBuilder();
    77     if (parentNode == null || parentNode.getNodeType() == Node.Type.ITEM)
     76    if (parentNode != null && parentNode.getNodeType() == Node.Type.ITEM)
    7877    {
    7978      if (titlePrefix != null) title.append(titlePrefix).append(": ");
  • trunk/src/core/net/sf/basedb/util/overview/validator/AnnotationValidator.java

    r5132 r5651  
    261261  */
    262262  @Override
    263   protected Fix getMissingItemFix(Node parentNode)
     263  protected Fix getMissingItemFix(DbControl dc, Node parentNode)
    264264  {
    265265    return null;
  • trunk/src/core/net/sf/basedb/util/overview/validator/AnyToAnyValidator.java

    r5500 r5651  
    8282  */
    8383  @Override
    84   protected Fix getMissingItemFix(Node parentNode)
     84  protected Fix getMissingItemFix(DbControl dc, Node parentNode)
    8585  {
    8686    return null;
  • trunk/src/core/net/sf/basedb/util/overview/validator/ArrayBatchValidator.java

    r4764 r5651  
    2323
    2424import net.sf.basedb.core.ArrayBatch;
     25import net.sf.basedb.core.DbControl;
    2526import net.sf.basedb.util.overview.Fix;
    2627import net.sf.basedb.util.overview.Validator;
     
    5657  */
    5758  @Override
    58   protected Fix getMissingItemFix(Node parentNode)
     59  protected Fix getMissingItemFix(DbControl dc, Node parentNode)
    5960  {
    6061    return new Fix("Add array batch to array slide", parentNode.getItem());
  • trunk/src/core/net/sf/basedb/util/overview/validator/ArrayDesignValidator.java

    r5650 r5651  
    117117  */
    118118  @Override
    119   protected Fix getMissingItemFix(Node parentNode)
     119  protected Fix getMissingItemFix(DbControl dc, Node parentNode)
    120120  {
    121121    Fix fix = null;
  • trunk/src/core/net/sf/basedb/util/overview/validator/ArraySlideValidator.java

    r4764 r5651  
    2323
    2424import net.sf.basedb.core.ArraySlide;
     25import net.sf.basedb.core.DbControl;
    2526import net.sf.basedb.util.overview.Fix;
    2627import net.sf.basedb.util.overview.Validator;
     
    5354  /**
    5455    The suggested fix is to add an array slide to the
    55     hybridization.
     56    bioassay.
    5657  */
    5758  @Override
    58   protected Fix getMissingItemFix(Node parentNode)
     59  protected Fix getMissingItemFix(DbControl dc, Node parentNode)
    5960  {
    60     return  new Fix("Add array slide to hybridization", parentNode.getItem());
     61    return  new Fix("Add array slide to bioassay", parentNode.getItem());
    6162  }
    6263  // ----------------------------
  • trunk/src/core/net/sf/basedb/util/overview/validator/BasicItemNodeValidatorFactory.java

    r5642 r5651  
    197197    registerCheckedNodeValidator(Item.ARRAYBATCH, ArrayBatchValidator.class);
    198198    registerCheckedNodeValidator(Item.ARRAYSLIDE, ArraySlideValidator.class);
    199     registerCheckedNodeValidator(Item.PHYSICALBIOASSAY, HybridizationValidator.class);
     199    registerCheckedNodeValidator(Item.PHYSICALBIOASSAY, PhysicalBioAssayValidator.class);
    200200    registerCheckedNodeValidator(Item.SCAN, ScanValidator.class);
    201201    registerCheckedNodeValidator(Item.RAWBIOASSAY, RawBioAssayValidator.class);
     
    204204//    // Property node validators
    205205    registerCheckedNodeValidator(Item.PROTOCOL, ProtocolValidator.class);
     206    registerCheckedNodeValidator(Item.TAG, TagValidator.class);
    206207    registerCheckedNodeValidator("PROTOCOL.PARAMETER", ProtocolParameterValidator.class);
    207208    registerCheckedNodeValidator("EXPERIMENTAL.FACTOR", ExperimentalFactorValidator.class);
  • trunk/src/core/net/sf/basedb/util/overview/validator/BasicNodeValidator.java

    r4768 r5651  
    7676    if (ruleMissing != null)
    7777    {
    78       context.createFailure(ruleMissing, parentNode, null, getMissingItemFix(parentNode));
     78      context.createFailure(ruleMissing, parentNode, null, getMissingItemFix(dc, parentNode));
    7979    }
    8080    return false;
     
    117117    if (ruleDenied != null)
    118118    {
    119       context.createFailure(ruleDenied, node, null, getDeniedItemFix(node, parentNode));
     119      context.createFailure(ruleDenied, node, null, getDeniedItemFix(dc, node, parentNode));
    120120    }
    121121  }
     
    146146    </pre>
    147147  */
    148   protected abstract Fix getMissingItemFix(Node parentNode);
     148  protected abstract Fix getMissingItemFix(DbControl dc, Node parentNode);
    149149 
    150150  /**
     
    152152    for an access denied problem. The default implementation does nothing.
    153153  */
    154   protected Fix getDeniedItemFix(Node node, Node parentNode)
     154  protected Fix getDeniedItemFix(DbControl dc, Node node, Node parentNode)
    155155  {
    156156    return null;
  • trunk/src/core/net/sf/basedb/util/overview/validator/BioSourceValidator.java

    r4764 r5651  
    2323
    2424import net.sf.basedb.core.BioSource;
     25import net.sf.basedb.core.DbControl;
     26import net.sf.basedb.core.Item;
    2527import net.sf.basedb.util.overview.Fix;
     28import net.sf.basedb.util.overview.OverviewContext;
    2629import net.sf.basedb.util.overview.Validator;
    2730import net.sf.basedb.util.overview.Node;
     
    5154    -------------------------
    5255  */
     56  @Override
     57  public void postValidate(DbControl dc, OverviewContext context, Node node, Node parentNode)
     58  {
     59    super.postValidate(dc, context, node, parentNode);
     60
     61    // If parent node contains a sample; check the subtypes
     62    if (parentNode != null && parentNode.getItemType() == Item.SAMPLE)
     63    {
     64      SampleValidator.checkParentBioSourceSubtype(dc, context, parentNode, node);
     65    }
     66  }
     67 
    5368  /**
    5469    @return Suggested fix is to add a biosource to the parent sample.
    5570  */
    5671  @Override
    57   protected Fix getMissingItemFix(Node sampleNode)
     72  protected Fix getMissingItemFix(DbControl dc, Node sampleNode)
    5873  {
    5974    return new Fix("Add biosource to sample", sampleNode.getItem());
    6075  }
    6176  // ----------------------------
    62 
     77 
    6378}
  • trunk/src/core/net/sf/basedb/util/overview/validator/DataFileValidator.java

    r5623 r5651  
    181181  */
    182182  @Override
    183   protected Fix getMissingItemFix(Node parentNode)
     183  protected Fix getMissingItemFix(DbControl dc, Node parentNode)
    184184  {
    185185    return null;
  • trunk/src/core/net/sf/basedb/util/overview/validator/ExperimentValidator.java

    r4816 r5651  
    7777  */
    7878  @Override
    79   protected Fix getMissingItemFix(Node parentNode)
     79  protected Fix getMissingItemFix(DbControl dc, Node parentNode)
    8080  {
    8181    return null;
  • trunk/src/core/net/sf/basedb/util/overview/validator/ExperimentalFactorValidator.java

    r4764 r5651  
    2323
    2424import net.sf.basedb.core.AnnotationType;
     25import net.sf.basedb.core.DbControl;
    2526import net.sf.basedb.util.overview.Fix;
    2627import net.sf.basedb.util.overview.Node;
     
    4546
    4647  @Override
    47   protected Fix getMissingItemFix(Node parentNode)
     48  protected Fix getMissingItemFix(DbControl dc, Node parentNode)
    4849  {
    4950    return null;
  • trunk/src/core/net/sf/basedb/util/overview/validator/ExtractValidator.java

    r5641 r5651  
    2323
    2424import net.sf.basedb.core.BasicItem;
     25import net.sf.basedb.core.DbControl;
    2526import net.sf.basedb.core.Extract;
    2627import net.sf.basedb.core.Item;
     28import net.sf.basedb.core.ItemSubtype;
     29import net.sf.basedb.core.PermissionDeniedException;
     30import net.sf.basedb.core.PhysicalBioAssay;
     31import net.sf.basedb.core.Sample;
    2732import net.sf.basedb.util.overview.Fix;
     33import net.sf.basedb.util.overview.OverviewContext;
    2834import net.sf.basedb.util.overview.Validator;
    2935import net.sf.basedb.util.overview.Node;
     36import net.sf.basedb.util.overview.Node.Type;
     37import net.sf.basedb.util.overview.node.ChildNodeDirection;
    3038
    3139/**
     
    3442  <li>Missing item: {@link Validator#MISSING_EXTRACT}
    3543  <li>Access denied: {@link Validator#DENIED_EXTRACT}
     44  <li>Subtype of parent extract: {@link Validator#INCORRECT_EXTRACT_TYPE}
     45  <li>Subtype of parent sample: {@link Validator#INCORRECT_SAMPLE_TYPE}
    3646  </ul>
    3747
     
    5363    -------------------------
    5464  */
     65  @Override
     66  public void postValidate(DbControl dc, OverviewContext context, Node node, Node parentNode)
     67  {
     68    super.postValidate(dc, context, node, parentNode);
     69
     70    if (parentNode != null)
     71    {
     72      Node parentItemNode = parentNode.getNodeType() == Type.ITEM ? parentNode : parentNode.getParent();
     73      Item parentType = parentItemNode.getItemType();
     74
     75      if (parentType == Item.SAMPLE)
     76      {
     77        checkParentSampleSubtype(dc, context, node, parentItemNode);
     78      }
     79      else if (parentType == Item.EXTRACT)
     80      {
     81        if (node.getChildNodeDirection() == ChildNodeDirection.FORWARD)
     82        {
     83          checkParentExtractSubtype(dc, context, node, parentItemNode);
     84        }
     85        else
     86        {
     87          checkParentExtractSubtype(dc, context, parentItemNode, node);
     88        }
     89      }
     90      else if (parentType == Item.PHYSICALBIOASSAY)
     91      {
     92        PhysicalBioAssayValidator.checkExtractSubtype(dc, context, parentItemNode, node);
     93      }
     94    }
     95  }
     96
     97 
    5598  /**
    56     The suggested fix is to add a parent extract to the
    57     labled extract or one or more extracts to the pooled extract.
     99    The suggested fix is to add parent extracts to the physical
     100    bioassay or one or more extracts to the pooled extract.
    58101  */
    59102  @Override
    60   protected Fix getMissingItemFix(Node parentNode)
     103  protected Fix getMissingItemFix(DbControl dc, Node parentNode)
    61104  {
    62105    Fix fix = null;
    63106    Item parentType = parentNode.getItemType();
    64107    BasicItem parentItem = parentNode.getItem();
    65     /*
    66108    if (parentType == Item.PHYSICALBIOASSAY)
    67109    {
    68       fix =  new Fix("Add parent extract to '" + ((LabeledExtract)parentItem).getName() + "'", parentItem);
     110      fix =  new Fix("Add extracts to '" + ((PhysicalBioAssay)parentItem).getName() + "'", parentItem);
    69111    }
    70     else */if (parentType == Item.EXTRACT)
     112    else if (parentType == Item.EXTRACT)
    71113    {
    72114      fix = new Fix("Add parent extracts to '" + ((Extract)parentItem).getName() + "'", parentItem);
     
    75117  }
    76118  // ----------------------------
     119 
     120 
     121  /**
     122    Check the subtype of the sample that is the parent to an extract. Given that
     123    the extract has a non-null subtype, which has a related SAMPLE subtype, this
     124    method checks if the parent sample has the same subtype. If there is no related
     125    subtype for the extract, any subtype for the parent is accepted.
     126    @since 3.0
     127  */
     128  public static void checkParentSampleSubtype(DbControl dc, OverviewContext context, Node extractNode, Node sampleNode)
     129  {
     130    Extract extract = (Extract)extractNode.getItem();
     131    Sample sample = (Sample)sampleNode.getItem();
     132   
     133    try
     134    {
     135      ItemSubtype expectedSubtype = ItemSubtype.getRelatedSubtype(dc, extract, Item.SAMPLE, Item.EXTRACT);
     136      ItemSubtype subtype = sample.getItemSubtype();
     137     
     138      if (expectedSubtype != null && !expectedSubtype.equals(subtype))
     139      {
     140        if (expectedSubtype.getMainItemType() == Item.SAMPLE)
     141        {
     142          context.createFailure(Validator.INCORRECT_SAMPLE_TYPE, extractNode,
     143            "Expected a parent sample with subtype: " + expectedSubtype.getName(),
     144            new Fix("Change parent sample or subtype of '" + extractNode.getTitle() + "'", extract),
     145            new Fix("Change subtype of '" + sample.getName() + "' to '" + expectedSubtype.getName() + "'", sample)
     146          );
     147        }
     148        else
     149        {
     150          context.createFailure(Validator.INCORRECT_SAMPLE_TYPE, extractNode,
     151            "Expected a parent extract with subtype: " + expectedSubtype.getName(),
     152            new Fix("Change parent sample or subtype of '" + extractNode.getTitle() + "'", extract)
     153          );
     154        }
     155      }
     156    }
     157    catch (PermissionDeniedException ex)
     158    {}
     159  }
     160
     161  /**
     162    Check the subtype of the extract that is the parent to another extract. Given that
     163    the child extract has a non-null subtype, which has a related EXTRACT subtype, this
     164    method checks if the parent extract has the same subtype. If there is no related
     165    subtype for the child extract, any subtype for the parent is accepted.
     166    @since 3.0
     167  */
     168  public static void checkParentExtractSubtype(DbControl dc, OverviewContext context, Node childNode, Node parentNode)
     169  {
     170    Extract child = (Extract)childNode.getItem();
     171    Extract parent = (Extract)parentNode.getItem();
     172   
     173    try
     174    {
     175      ItemSubtype expectedSubtype = ItemSubtype.getRelatedSubtype(dc, child, Item.EXTRACT, 0);
     176      ItemSubtype subtype = parent.getItemSubtype();
     177     
     178      if (expectedSubtype != null && !expectedSubtype.equals(subtype))
     179      {
     180        context.createFailure(Validator.INCORRECT_EXTRACT_TYPE, childNode,
     181          "Expected a parent extract with subtype: " + expectedSubtype.getName(),
     182          new Fix("Change parent extract or subtype of '" + childNode.getTitle() + "'", child),
     183          new Fix("Change subtype of '" + parent.getName() + "' to '" + expectedSubtype.getName() + "'", parent)
     184        );
     185      }
     186    }
     187    catch (PermissionDeniedException ex)
     188    {}
     189  }
     190
     191 
    77192}
  • trunk/src/core/net/sf/basedb/util/overview/validator/HardwareValidator.java

    r5650 r5651  
    2525import net.sf.basedb.core.DbControl;
    2626import net.sf.basedb.core.Hardware;
     27import net.sf.basedb.core.Item;
     28import net.sf.basedb.core.ItemSubtype;
    2729import net.sf.basedb.core.PermissionDeniedException;
    2830import net.sf.basedb.core.Project;
     31import net.sf.basedb.core.Subtypable;
     32import net.sf.basedb.core.SystemItems;
    2933import net.sf.basedb.util.overview.Fix;
    3034import net.sf.basedb.util.overview.OverviewContext;
     
    5155  public HardwareValidator()
    5256  {
    53     super(Validator.MISSING_HARDWARE, Validator.DENIED_HARDWARE);
     57    super(null, Validator.DENIED_HARDWARE);
    5458  }
    5559
     
    6064  */
    6165  /**
    62     Checks if the software is of the correct software type
    63     and, if a project is active, the software is the same as
    64     the default for the project.
     66    If the parent item has a subtype that is related to a HARDWARE subtype, report
     67    the missing item as a {@link Validator#MISSING_HARDWARE} failure. Otherwise,
     68    ignore the missing hardware.
     69    @return Always false
     70  */
     71  @Override
     72  public boolean preMissingItem(DbControl dc, OverviewContext context, Node parentNode)
     73  {
     74    BasicItem parentItem = parentNode.getItem();
     75    ItemSubtype expectedSubtype = getExpectedHardwareSubtype(dc, parentItem);
     76    if (expectedSubtype != null)
     77    {
     78      context.createFailure(Validator.MISSING_HARDWARE, parentNode,
     79          "Missing " + expectedSubtype.getName().toLowerCase(), getMissingItemFix(dc, parentNode));
     80    }
     81    return false;
     82  }
     83 
     84  /**
     85    Checks if the hardware is of the correct hardware type
     86    and, if a project is active, the hardware is included as a
     87    default hardware for the project.
    6588  */
    6689  @Override
     
    6992    super.postValidate(dc, context, node, parentNode);
    7093    Hardware hardware = (Hardware)node.getItem();
     94   
    7195    BasicItem parentItem = parentNode.getItem();
    72     //Project.Default defaultType = Project.getDefaultType(Item.HARDWARE, parentNode.getItemType());
    73     String hardwareTypeName = "hardware";
    74     String parentTypeName = parentNode.getItemType().toString().toLowerCase();
    75     /*
    76     if (defaultType != null)
     96    ItemSubtype expectedSubtype = getExpectedHardwareSubtype(dc, parentItem);
     97    try
    7798    {
    78       hardwareTypeName = defaultType.getShortName().toLowerCase();
    79       parentTypeName = defaultType.getAttachesToItemType().toString().toLowerCase();
     99      ItemSubtype subtype = hardware.getItemSubtype();
     100      if (expectedSubtype != null && !expectedSubtype.equals(subtype))
     101      {
     102        context.createFailure(Validator.INCORRECT_HARDWARETYPE, parentNode,
     103          "Expected a hardware with subtype: " + expectedSubtype.getName(),
     104          new Fix("Change hardware of '" + parentNode.getTitle() + "'", parentItem),
     105          new Fix("Change hardware type of '" + hardware.getName() + "' to '" + expectedSubtype.getName() + "'", hardware)
     106        );
     107      }
    80108    }
    81     */
    82    
     109    catch (PermissionDeniedException ex)
     110    {}
     111
    83112    // Check if using project default hardware
    84113    Project project = context.getProject();
    85 //    BasicItem defaultHardware = OverviewUtil.getProjectDefaultItem(dc, project, defaultType);
    86114    if (!project.isDefaultItem(hardware))
    87115    {
    88116      context.createFailure(Validator.NONDEFAULT_HARDWARE, parentNode, null,
    89         new Fix("Change " + hardwareTypeName + " of " + parentTypeName, parentItem),
    90         new Fix("Change default " + hardwareTypeName + " for project", project)
     117        new Fix("Change hardware of '" + parentNode.getTitle() + "'", parentItem),
     118        new Fix("Add '" + hardware.getName() + "' as default hardware to project", project)
    91119      );
    92120    }
    93 
    94     // Check hardware subtype
    95     try
    96     {
    97       /*
    98       ItemSubtype ht = hardware.getItemSubtype();
    99       String requiredId = defaultType == null ? null : defaultType.getType();
    100       if (requiredId != null && !requiredId.equals(ht.getSystemId()))
    101       {
    102         context.createFailure(Validator.INCORRECT_HARDWARETYPE, parentNode, null,
    103           new Fix("Change " + hardwareTypeName + " of " + parentTypeName, parentItem),
    104           new Fix("Change hardware type to '" + hardwareTypeName + "'", hardware)
    105         );
    106       }
    107       */
    108     }
    109     catch (PermissionDeniedException ex)
    110     {}
    111121  }
    112122 
     
    115125  */
    116126  @Override
    117   protected Fix getMissingItemFix(Node parentNode)
     127  protected Fix getMissingItemFix(DbControl dc, Node parentNode)
    118128  {
    119     //Project.Default defaultType = Project.getDefaultType(Item.HARDWARE, parentNode.getItemType());
    120     String hardwareTypeName = "hardware";
    121     String parentTypeName = parentNode.getItemType().toString().toLowerCase();
    122     /*
    123     if (defaultType != null)
    124     {
    125       hardwareTypeName = defaultType.getShortName().toLowerCase();
    126       parentTypeName = defaultType.getAttachesToItemType().toString().toLowerCase();
    127     }
    128     */
    129     BasicItem parentItem = parentNode.getItem();
    130     return new Fix("Add " + hardwareTypeName + " to " + parentTypeName, parentItem);
     129    BasicItem parentItem = parentNode.getItem();   
     130    return new Fix("Add hardware to '" + parentNode.getTitle() + "'", parentItem);
    131131  }
    132132  // --------------------------------
     133 
     134 
     135  /**
     136    Get the subtype of the associated hardware that we expect for the given
     137    parent item.
     138  */
     139  protected ItemSubtype getExpectedHardwareSubtype(DbControl dc, BasicItem parentItem)
     140  {
     141    ItemSubtype expectedSubtype = null;
     142    int defaultSubtypeForItemType = SystemItems.getId(Hardware.getDefaultSystemId(parentItem.getType()));
     143    try
     144    {
     145      if (parentItem instanceof Subtypable)
     146      {
     147        expectedSubtype = ItemSubtype.getRelatedSubtype(dc,
     148            (Subtypable)parentItem, Item.HARDWARE, defaultSubtypeForItemType);
     149      }
     150      else if (defaultSubtypeForItemType != 0)
     151      {
     152        expectedSubtype = ItemSubtype.getById(dc, defaultSubtypeForItemType);
     153      }
     154    }
     155    catch (PermissionDeniedException ex)
     156    {}
     157    return expectedSubtype;
     158  }
     159
     160 
    133161}
  • trunk/src/core/net/sf/basedb/util/overview/validator/PhysicalBioAssayValidator.java

    r5642 r5651  
    2222package net.sf.basedb.util.overview.validator;
    2323
     24import net.sf.basedb.core.DbControl;
     25import net.sf.basedb.core.Extract;
     26import net.sf.basedb.core.ItemSubtype;
     27import net.sf.basedb.core.PermissionDeniedException;
    2428import net.sf.basedb.core.PhysicalBioAssay;
    2529import net.sf.basedb.core.Item;
    2630import net.sf.basedb.util.overview.Fix;
     31import net.sf.basedb.util.overview.OverviewContext;
    2732import net.sf.basedb.util.overview.Validator;
    2833import net.sf.basedb.util.overview.Node;
     34import net.sf.basedb.util.overview.Node.Type;
    2935
    3036/**
    31   Validator implementation for hybridizations. Validation rules:
     37  Validator implementation for physical bioassays. Validation rules:
    3238  <ul>
    33   <li>Missing item: {@link Validator#MISSING_HYBRIDIZATION}
    34   <li>Access denied: {@link Validator#DENIED_HYBRIDIZATION}
     39  <li>Missing item: {@link Validator#MISSING_BIOASSAY}
     40  <li>Access denied: {@link Validator#DENIED_BIOASSAY}
     41  <li>Subtype of parent extract: {@link Validator#INCORRECT_EXTRACT_TYPE}
    3542  </ul>
    3643
     
    3946  @base.modified $Date$
    4047*/
    41 public class HybridizationValidator
     48public class PhysicalBioAssayValidator
    4249  extends NameableNodeValidator<PhysicalBioAssay>
    4350{
    4451 
    45   public HybridizationValidator()
     52  public PhysicalBioAssayValidator()
    4653  {
    47     super(Validator.MISSING_HYBRIDIZATION, Validator.DENIED_HYBRIDIZATION);
     54    super(Validator.MISSING_BIOASSAY, Validator.DENIED_BIOASSAY);
    4855  }
    4956
     
    5158    From BasicValidator class
    5259    -------------------------
    53   */
     60  */ 
     61  @Override
     62  public void postValidate(DbControl dc, OverviewContext context, Node node, Node parentNode)
     63  {
     64    super.postValidate(dc, context, node, parentNode);
     65   
     66    if (parentNode != null)
     67    {
     68      Node parentItemNode = parentNode.getNodeType() == Type.ITEM ? parentNode : parentNode.getParent();
     69      Item parentType = parentItemNode.getItemType();
     70
     71      if (parentType == Item.EXTRACT)
     72      {
     73        checkExtractSubtype(dc, context, node, parentItemNode);
     74      }
     75    }
     76
     77  }
     78
    5479  /**
    5580    @return Suggested fix is to add a scan to the parent raw bioassay.
    5681  */
    5782  @Override
    58   protected Fix getMissingItemFix(Node parentNode)
     83  protected Fix getMissingItemFix(DbControl dc, Node parentNode)
    5984  {
    6085    Fix fix = null;
    6186    if (parentNode.getItemType() == Item.SCAN)
    6287    {
    63       fix = new Fix("Add hybridization to scan", parentNode.getItem());
     88      fix = new Fix("Add bioassay to scan", parentNode.getItem());
    6489    }
    6590    return fix;
     
    6792  // ----------------------------
    6893
     94 
     95  /**
     96    Check the subtype of the extract that is the parent to a physical bioassay. Given that
     97    the bioassay has a non-null subtype, which has a related EXTRACT subtype, this
     98    method checks if the parent extract has the same subtype. If there is no related
     99    subtype for the bioassay, any subtype for the parent is accepted.
     100  */
     101  public static void checkExtractSubtype(DbControl dc, OverviewContext context, Node bioAssayNode, Node extractNode)
     102  {
     103    PhysicalBioAssay bioAssay = (PhysicalBioAssay)bioAssayNode.getItem();
     104    Extract extract = (Extract)extractNode.getItem();
     105   
     106    try
     107    {
     108      ItemSubtype expectedSubtype = ItemSubtype.getRelatedSubtype(dc, bioAssay, Item.EXTRACT, 0);
     109      ItemSubtype subtype = extract.getItemSubtype();
     110     
     111      if (expectedSubtype != null && !expectedSubtype.equals(subtype))
     112      {
     113        context.createFailure(Validator.INCORRECT_EXTRACT_TYPE, bioAssayNode,
     114          "Expected a parent extract with subtype: " + expectedSubtype.getName(),
     115          new Fix("Change parent extract or subtype of '" + bioAssayNode.getTitle() + "'", bioAssay),
     116          new Fix("Change subtype of '" + extract.getName() + "' to '" + expectedSubtype.getName() + "'", extract)
     117        );
     118      }
     119    }
     120    catch (PermissionDeniedException ex)
     121    {}
     122  }
     123
    69124}
  • trunk/src/core/net/sf/basedb/util/overview/validator/PlatformValidator.java

    r5650 r5651  
    103103  */
    104104  @Override
    105   protected Fix getMissingItemFix(Node parentNode)
     105  protected Fix getMissingItemFix(DbControl dc, Node parentNode)
    106106  {
    107107    return null;
  • trunk/src/core/net/sf/basedb/util/overview/validator/ProtocolParameterValidator.java

    r4764 r5651  
    117117  */
    118118  @Override
    119   protected Fix getMissingItemFix(Node parentNode)
     119  protected Fix getMissingItemFix(DbControl dc, Node parentNode)
    120120  {
    121121    return null;
  • trunk/src/core/net/sf/basedb/util/overview/validator/ProtocolValidator.java

    r5650 r5651  
    2929import net.sf.basedb.core.Project;
    3030import net.sf.basedb.core.Protocol;
     31import net.sf.basedb.core.Subtypable;
     32import net.sf.basedb.core.SystemItems;
    3133import net.sf.basedb.util.overview.Fix;
    3234import net.sf.basedb.util.overview.OverviewContext;
    33 import net.sf.basedb.util.overview.OverviewUtil;
    3435import net.sf.basedb.util.overview.Validator;
    3536import net.sf.basedb.util.overview.Node;
     
    5455  public ProtocolValidator()
    5556  {
    56     super(Validator.MISSING_PROTOCOL, Validator.DENIED_PROTOCOL);
     57    super(null, Validator.DENIED_PROTOCOL);
    5758  }
    5859
     
    6263    -----------------------------
    6364  */
     65  /**
     66    If the parent item has a subtype that is related to a PROTOCOL subtype, report
     67    the missing item as a {@link Validator#MISSING_PROTOCOL} failure. Otherwise,
     68    ignore the missing protocol.
     69    @return Always false
     70  */
     71  @Override
     72  public boolean preMissingItem(DbControl dc, OverviewContext context, Node parentNode)
     73  {
     74    BasicItem parentItem = parentNode.getItem();
     75    ItemSubtype expectedSubtype = getExpectedProtocolSubtype(dc, parentItem);
     76    if (expectedSubtype != null)
     77    {
     78      context.createFailure(Validator.MISSING_PROTOCOL, parentNode,
     79          null, getMissingItemFix(dc, parentNode));
     80    }
     81    return false;
     82  }
     83 
    6484  /**
    6585    Checks if the protocol is of the correct protocol type
     
    7292    super.postValidate(dc, context, node, parentNode);
    7393    Protocol protocol = (Protocol)node.getItem();
     94   
     95    // Validate the subtype of the protocol
    7496    BasicItem parentItem = parentNode.getItem();
    75 //    Project.Default defaultType = Project.getDefaultType(Item.PROTOCOL, parentNode.getItemType());
    76     String protocolTypeName = "protocol";
    77     String parentTypeName = parentNode.getItemType().toString().toLowerCase();
    78     /*
    79     if (defaultType != null)
     97    ItemSubtype expectedSubtype = getExpectedProtocolSubtype(dc, parentItem);
     98    try
    8099    {
    81       protocolTypeName = defaultType.getShortName().toLowerCase();
    82       parentTypeName = defaultType.getAttachesToItemType().toString().toLowerCase();
     100      ItemSubtype subtype = protocol.getItemSubtype();
     101      if (expectedSubtype != null && !expectedSubtype.equals(subtype))
     102      {
     103        context.createFailure(Validator.INCORRECT_PROTOCOLTYPE, parentNode,
     104          "Expected a protocol with subtype: " + expectedSubtype.getName(),
     105          new Fix("Change protocol of '" + parentNode.getTitle() + "'", parentItem),
     106          new Fix("Change protocol type of '" + protocol.getName() + "' to '" + expectedSubtype.getName() + "'", protocol)
     107        );
     108      }
    83109    }
    84     */
    85    
     110    catch (PermissionDeniedException ex)
     111    {}
     112
    86113    // Check if using project default protocol
    87114    Project project = context.getProject();
    88 //    BasicItem defaultProtocol = OverviewUtil.getProjectDefaultItem(dc, project, defaultType);
    89115    if (!project.isDefaultItem(protocol))
    90116    {
    91117      context.createFailure(Validator.NONDEFAULT_PROTOCOL, parentNode, null,
    92         new Fix("Change protocol of " + parentTypeName, parentItem),
    93         new Fix("Change default " + protocolTypeName + " for project", project)
     118        new Fix("Change protocol of '" + parentNode.getTitle() + "'", parentItem),
     119        new Fix("Add '" + protocol.getName() + "' as default protocol to project", project)
    94120      );
    95121    }
    96 
    97     // Check protocol subtype
    98     try
    99     {
    100       /*
    101       ItemSubtype pt = protocol.getItemSubtype();
    102       String requiredId = defaultType == null ? null : defaultType.getType();
    103       if (requiredId != null && !requiredId.equals(pt.getSystemId()))
    104       {
    105         context.createFailure(Validator.INCORRECT_PROTOCOLTYPE, parentNode, null,
    106           new Fix("Change protocol of " + parentTypeName, parentItem),
    107           new Fix("Change protocol type to '" + protocolTypeName + "'", protocol)
    108         );
    109       }
    110       */
    111     }
    112     catch (PermissionDeniedException ex)
    113     {}
    114122  }
    115123 
     
    118126  */
    119127  @Override
    120   protected Fix getMissingItemFix(Node parentNode)
     128  protected Fix getMissingItemFix(DbControl dc, Node parentNode)
    121129  {
    122 //    Project.Default defaultType = Project.getDefaultType(Item.PROTOCOL, parentNode.getItemType());
    123     String parentTypeName = parentNode.getItemType().toString().toLowerCase();
    124     /*
    125     if (defaultType != null)
    126     {
    127       parentTypeName = defaultType.getAttachesToItemType().toString().toLowerCase();
    128     }
    129     */
    130130    BasicItem parentItem = parentNode.getItem();
    131     return new Fix("Add protocol to " + parentTypeName, parentItem);
     131    return new Fix("Add protocol to '" + parentNode.getTitle() + "'", parentItem);
    132132  }
    133133  // --------------------------------
     134 
     135  /**
     136    Get the subtype of the associated protocol that we expect for the given
     137    parent item.
     138  */
     139  protected ItemSubtype getExpectedProtocolSubtype(DbControl dc, BasicItem parentItem)
     140  {
     141    ItemSubtype expectedSubtype = null;
     142    int defaultSubtypeForItemType = SystemItems.getId(Protocol.getDefaultSystemId(parentItem.getType()));
     143    try
     144    {
     145      if (parentItem instanceof Subtypable)
     146      {
     147        expectedSubtype = ItemSubtype.getRelatedSubtype(dc,
     148            (Subtypable)parentItem, Item.PROTOCOL, defaultSubtypeForItemType, 0);
     149      }
     150      else if (defaultSubtypeForItemType != 0)
     151      {
     152        expectedSubtype = ItemSubtype.getById(dc, defaultSubtypeForItemType);
     153      }
     154    }
     155    catch (PermissionDeniedException ex)
     156    {}
     157    return expectedSubtype;
     158  }
     159
     160 
    134161}
  • trunk/src/core/net/sf/basedb/util/overview/validator/RawBioAssayValidator.java

    r5642 r5651  
    183183  */
    184184  @Override
    185   protected Fix getMissingItemFix(Node parentNode)
     185  protected Fix getMissingItemFix(DbControl dc, Node parentNode)
    186186  {
    187187    return null;
  • trunk/src/core/net/sf/basedb/util/overview/validator/SampleValidator.java

    r4764 r5651  
    2323
    2424import net.sf.basedb.core.BasicItem;
     25import net.sf.basedb.core.BioSource;
     26import net.sf.basedb.core.DbControl;
    2527import net.sf.basedb.core.Extract;
    2628import net.sf.basedb.core.Item;
     29import net.sf.basedb.core.ItemSubtype;
     30import net.sf.basedb.core.PermissionDeniedException;
    2731import net.sf.basedb.core.Sample;
    2832import net.sf.basedb.util.overview.Fix;
     33import net.sf.basedb.util.overview.Node.Type;
     34import net.sf.basedb.util.overview.OverviewContext;
    2935import net.sf.basedb.util.overview.Validator;
    3036import net.sf.basedb.util.overview.Node;
     37import net.sf.basedb.util.overview.node.ChildNodeDirection;
    3138
    3239/**
     
    3542  <li>Missing item: {@link Validator#MISSING_SAMPLE}
    3643  <li>Access denied: {@link Validator#DENIED_SAMPLE}
     44  <li>Subtype of parent sample: {@link Validator#INCORRECT_SAMPLE_TYPE}
     45  <li>Subtype of parent biosource: {@link Validator#INCORRECT_BIOSOURCE_TYPE}
    3746  </ul>
    3847
     
    5463    -------------------------
    5564  */
     65  @Override
     66  public void postValidate(DbControl dc, OverviewContext context, Node node, Node parentNode)
     67  {
     68    super.postValidate(dc, context, node, parentNode);
     69
     70    if (parentNode != null)
     71    {
     72      Node parentItemNode = parentNode.getNodeType() == Type.ITEM ? parentNode : parentNode.getParent();
     73      Item parentType = parentItemNode.getItemType();
     74
     75      if (parentType == Item.BIOSOURCE)
     76      {
     77        checkParentBioSourceSubtype(dc, context, node, parentItemNode);
     78      }
     79      else if (parentType == Item.SAMPLE)
     80      {
     81        if (node.getChildNodeDirection() == ChildNodeDirection.FORWARD)
     82        {
     83          checkParentSampleSubtype(dc, context, node, parentItemNode);
     84        }
     85        else
     86        {
     87          checkParentSampleSubtype(dc, context, parentItemNode, node);
     88        }
     89      }
     90      else if (parentType == Item.EXTRACT)
     91      {
     92        ExtractValidator.checkParentSampleSubtype(dc, context, parentItemNode, node);
     93      }
     94    }
     95  }
     96
     97 
    5698  /**
    5799    The suggested fix is to add a parent sample to the extract
     
    59101  */
    60102  @Override
    61   protected Fix getMissingItemFix(Node parentNode)
     103  protected Fix getMissingItemFix(DbControl dc, Node parentNode)
    62104  {
    63105    Fix fix = null;
     
    75117  }
    76118  // ----------------------------
     119
     120  /**
     121    Check the subtype of the biosurce that is the parent to a sample. Given that
     122    the sample has a non-null subtype, which has a related BIOSOURCE subtype, this
     123    method checks if the parent biosource has the same subtype. If there is no related
     124    subtype for the sample, any subtype for the parent is accepted.
     125    @since 3.0
     126  */
     127  public static void checkParentBioSourceSubtype(DbControl dc, OverviewContext context, Node sampleNode, Node bioSourceNode)
     128  {
     129    Sample sample = (Sample)sampleNode.getItem();
     130    BioSource bioSource = (BioSource)bioSourceNode.getItem();
     131   
     132    try
     133    {
     134      ItemSubtype expectedSubtype = ItemSubtype.getRelatedSubtype(dc, sample, Item.BIOSOURCE, Item.SAMPLE);
     135      ItemSubtype subtype = bioSource.getItemSubtype();
     136     
     137      if (expectedSubtype != null && !expectedSubtype.equals(subtype))
     138      {
     139        if (expectedSubtype.getMainItemType() == Item.BIOSOURCE)
     140        {
     141          // Expected another biosource subtype
     142          context.createFailure(Validator.INCORRECT_BIOSOURCE_TYPE, sampleNode,
     143            "Expected a parent biosource with subtype: " + expectedSubtype.getName(),
     144            new Fix("Change parent biosource or subtype of '" + sampleNode.getTitle() + "'", sample),
     145            new Fix("Change subtype of '" + bioSource.getName() + "' to '" + expectedSubtype.getName() + "'", bioSource)
     146          );
     147        }
     148        else
     149        {
     150          // Expected a sample as parent
     151          context.createFailure(Validator.INCORRECT_BIOSOURCE_TYPE, sampleNode,
     152              "Expected a parent sample with subtype: " + expectedSubtype.getName(),
     153              new Fix("Change parent biosource or subtype of '" + sampleNode.getTitle() + "'", sample)
     154            );
     155        }
     156      }
     157    }
     158    catch (PermissionDeniedException ex)
     159    {}
     160  }
     161 
     162  /**
     163    Check the subtype of the sample that is the parent to another sample. Given that
     164    the child sample has a non-null subtype, which has a related SAMPLE subtype, this
     165    method checks if the parent sample has the same subtype. If there is no related
     166    subtype for the child sample, any subtype for the parent is accepted.
     167    @since 3.0
     168  */
     169  public static void checkParentSampleSubtype(DbControl dc, OverviewContext context, Node childNode, Node parentNode)
     170  {
     171    Sample child = (Sample)childNode.getItem();
     172    Sample parent = (Sample)parentNode.getItem();
     173   
     174    try
     175    {
     176      ItemSubtype expectedSubtype = ItemSubtype.getRelatedSubtype(dc, child, Item.SAMPLE);
     177      ItemSubtype subtype = parent.getItemSubtype();
     178     
     179      if (expectedSubtype != null && !expectedSubtype.equals(subtype))
     180      {
     181        context.createFailure(Validator.INCORRECT_SAMPLE_TYPE, childNode,
     182          "Expected a parent sample with subtype: " + expectedSubtype.getName(),
     183          new Fix("Change parent sample or subtype of '" + childNode.getTitle() + "'", child),
     184          new Fix("Change subtype of '" + parent.getName() + "' to '" + expectedSubtype.getName() + "'", parent)
     185        );
     186      }
     187    }
     188    catch (PermissionDeniedException ex)
     189    {}
     190  }
     191
     192
    77193}
  • trunk/src/core/net/sf/basedb/util/overview/validator/ScanValidator.java

    r4764 r5651  
    2222package net.sf.basedb.util.overview.validator;
    2323
     24import net.sf.basedb.core.DbControl;
    2425import net.sf.basedb.core.Scan;
    2526import net.sf.basedb.util.overview.Fix;
     
    5556  */
    5657  @Override
    57   protected Fix getMissingItemFix(Node rawBioAssayNode)
     58  protected Fix getMissingItemFix(DbControl dc, Node rawBioAssayNode)
    5859  {
    5960    return new Fix("Add scan to raw bioassay", rawBioAssayNode.getItem());
  • trunk/src/core/net/sf/basedb/util/overview/validator/SoftwareValidator.java

    r5650 r5651  
    2929import net.sf.basedb.core.Project;
    3030import net.sf.basedb.core.Software;
     31import net.sf.basedb.core.Subtypable;
     32import net.sf.basedb.core.SystemItems;
    3133import net.sf.basedb.util.overview.Fix;
    3234import net.sf.basedb.util.overview.OverviewContext;
    33 import net.sf.basedb.util.overview.OverviewUtil;
    3435import net.sf.basedb.util.overview.Validator;
    3536import net.sf.basedb.util.overview.Node;
     
    7273    super.postValidate(dc, context, node, parentNode);
    7374    Software software = (Software)node.getItem();
     75   
     76    // Validate the subtype of the software
    7477    BasicItem parentItem = parentNode.getItem();
    75   //  Project.Default defaultType = Project.getDefaultType(Item.SOFTWARE, parentNode.getItemType());
    76     String softwareTypeName = "software";
    77     String parentTypeName = parentNode.getItemType().toString().toLowerCase();
    78     /*
    79     if (defaultType != null)
     78    ItemSubtype expectedSubtype = getExpectedSoftwareSubtype(dc, parentItem);
     79    try
    8080    {
    81       softwareTypeName = defaultType.getShortName().toLowerCase();
    82       parentTypeName = defaultType.getAttachesToItemType().toString().toLowerCase();
     81      ItemSubtype subtype = software.getItemSubtype();
     82      if (expectedSubtype != null && !expectedSubtype.equals(subtype))
     83      {
     84        context.createFailure(Validator.INCORRECT_SOFTWARETYPE, parentNode,
     85          "Expected a software with subtype: " + expectedSubtype.getName(),
     86          new Fix("Change software of '" + parentNode.getTitle() + "'", parentItem),
     87          new Fix("Change software type of '" + software.getName() + "' to '" + expectedSubtype.getName() + "'", software)
     88        );
     89      }
    8390    }
    84     */
     91    catch (PermissionDeniedException ex)
     92    {}
    8593   
    8694    // Check if using project default software
    8795    Project project = context.getProject();
    88   //  BasicItem defaultSoftware = OverviewUtil.getProjectDefaultItem(dc, project, defaultType);
    8996    if (!project.isDefaultItem(software))
    9097    {
    9198      context.createFailure(Validator.NONDEFAULT_SOFTWARE, parentNode, null,
    92         new Fix("Change " + softwareTypeName + " of " + parentTypeName, parentItem),
    93         new Fix("Change default " + softwareTypeName + " for project", project)
     99        new Fix("Change software of '" + parentNode.getTitle() + "'", parentItem),
     100        new Fix("Add '" + software.getName() + "' as default software to project", project)
    94101      );
    95102    }
    96      
    97     // Check software subtype
    98     try
    99     {
    100       ItemSubtype st = software.getItemSubtype();
    101       /*
    102       String requiredId = defaultType == null ? null : defaultType.getType();
    103       if (requiredId != null && !requiredId.equals(st.getSystemId()))
    104       {
    105         context.createFailure(Validator.INCORRECT_SOFTWARETYPE, parentNode, null,
    106           new Fix("Change  " + softwareTypeName + " of " + parentTypeName, parentItem),
    107           new Fix("Change software type to '" + softwareTypeName + "'", software)
    108         );
    109       }
    110       */
    111     }
    112     catch (PermissionDeniedException ex)
    113     {}
    114103  }
    115104
     
    119108  */
    120109  @Override
    121   protected Fix getMissingItemFix(Node parentNode)
     110  protected Fix getMissingItemFix(DbControl dc, Node parentNode)
    122111  {
    123 //    Project.Default defaultType = Project.getDefaultType(Item.SOFTWARE, parentNode.getItemType());
    124     String softwareTypeName = "software";
    125     String parentTypeName = parentNode.getItemType().toString().toLowerCase();
    126     /*
    127     if (defaultType != null)
    128     {
    129       softwareTypeName = defaultType.getShortName().toLowerCase();
    130       parentTypeName = defaultType.getAttachesToItemType().toString().toLowerCase();
    131     }
    132     */
    133     BasicItem parentItem = parentNode.getItem();
    134     return new Fix("Add " + softwareTypeName + " to " + parentTypeName, parentItem);
     112    BasicItem parentItem = parentNode.getItem();   
     113    return new Fix("Add software to '" + parentNode.getTitle() + "'", parentItem);
    135114  }
    136115  // --------------------------------
     116 
     117  /**
     118    Get the subtype of the associated software that we expect for the given
     119    parent item.
     120  */
     121  protected ItemSubtype getExpectedSoftwareSubtype(DbControl dc, BasicItem parentItem)
     122  {
     123    ItemSubtype expectedSubtype = null;
     124    int defaultSubtypeForItemType = SystemItems.getId(Software.getDefaultSystemId(parentItem.getType()));
     125    try
     126    {
     127      if (parentItem instanceof Subtypable)
     128      {
     129        expectedSubtype = ItemSubtype.getRelatedSubtype(dc,
     130            (Subtypable)parentItem, Item.SOFTWARE, defaultSubtypeForItemType);
     131      }
     132      else if (defaultSubtypeForItemType != 0)
     133      {
     134        expectedSubtype = ItemSubtype.getById(dc, defaultSubtypeForItemType);
     135      }
     136    }
     137    catch (PermissionDeniedException ex)
     138    {}
     139    return expectedSubtype;
     140  }
     141 
    137142}
  • trunk/www/common/overview/ajax.jsp

    r5556 r5651  
    2626  import="net.sf.basedb.core.Annotation"
    2727  import="net.sf.basedb.core.AnnotationType"
     28  import="net.sf.basedb.core.ItemSubtype"
     29  import="net.sf.basedb.core.Subtypable"
    2830  import="net.sf.basedb.core.Item"
    2931  import="net.sf.basedb.util.overview.GenericOverview"
     
    8890          catch (Throwable t)
    8991          {}
    90         }       
     92        }
     93        String subtitle = null;
     94        if (n.getNodeType() == Node.Type.FOLDER)
     95        {
     96          subtitle = n.getChildren() == null ? "0" : Integer.toString(n.getChildren().size());
     97        }
     98        else if (n.getItem() instanceof Subtypable)
     99        {
     100          try
     101          {
     102            ItemSubtype subtype = ((Subtypable)n.getItem(dc)).getItemSubtype();
     103            if (subtype != null) subtitle = subtype.getName();
     104          }
     105          catch (Throwable t)
     106          {}
     107        }
     108       
    91109        int numChildren = n.numChildren();
    92110        JSONObject jsonNode = new JSONObject();
    93111        jsonNode.put("id", n.getId());
    94         jsonNode.put("title", n.getTitle() + (n.getNodeType() == Node.Type.FOLDER ? " (" + numChildren + ")" : ""));
     112        jsonNode.put("title", n.getTitle() + (subtitle != null ? " <span class=\"subtitle\">(" + subtitle + ")</span>" : ""));
    95113        jsonNode.put("folderIcon", folderIcon);
    96114        jsonNode.put("numChildren", numChildren);
  • trunk/www/common/overview/frameset.jsp

    r5426 r5651  
    3939<base:page type="frameset" title="">
    4040  <base:head />
    41   <frameset cols="300,*" frameborder="yes" border="5">
     41  <frameset cols="400,*" frameborder="yes" border="5">
    4242    <frame name="tree"
    4343      src="tree.jsp?ID=<%=ID%>&show_failures=<%=showFailures%>"
    4444      scrolling="auto" marginwidth="0" marginheight="4" frameborder="1"
    4545    >
    46     <frameset rows="*,200" framborder="yes" border="5">
     46    <frameset rows="*,250" framborder="yes" border="5">
    4747      <frame name="info"
    4848        src="info.jsp?ID=<%=ID%>&show_failures=<%=showFailures%>"
  • trunk/www/common/overview/info.jsp

    r5500 r5651  
    3131  import="net.sf.basedb.core.AnnotationType"
    3232  import="net.sf.basedb.core.Annotation"
     33  import="net.sf.basedb.core.ItemSubtype"
     34  import="net.sf.basedb.core.Subtypable"
    3335  import="net.sf.basedb.core.AnyToAny"
    3436  import="net.sf.basedb.core.Protocol"
     
    6971<%@ taglib prefix="tbl" uri="/WEB-INF/table.tld" %>
    7072<%!
    71 private String getPath(String ID, Node node)
     73private String getPath(DbControl dc, String ID, Node node)
    7274{
    7375  Node parent = node.getParent();
    7476  if (parent == null) return "";
    75   String path = getPath(ID, parent);
     77  String path = getPath(dc, ID, parent);
    7678  if (parent.getNodeType() == Node.Type.FOLDER)
    7779  {
     
    8688    }
    8789    path += Base.getLink(ID, parent.getTitle(), item.getType(), item.getId(), item.hasPermission(Permission.WRITE));
     90   
     91    if (item instanceof Subtypable)
     92    {
     93      ItemSubtype subtype = ((Subtypable)parent.getItem(dc)).getItemSubtype();
     94      if (subtype != null)
     95      {
     96        path += " <span class=\"subtype\">(" + Base.getLinkedName(ID, subtype, false, true) + ")</span>";
     97      }
     98    }
     99   
    88100//    path += "<a href=\"javascript:Main.editItem('" + item.getType().name() + "', " + item.getId() +
    89101//      ")\" title=\"Edit this item\" style=\"padding-right: 4px; white-space: nowrap;\">" + HTML.encodeTags(parent.getTitle()) + "</a>";
     
    109121  if (node == null) node = overview.getRootNode();
    110122
    111   BasicItem item = node.getItem();
     123  BasicItem item = node.getItem(dc);
    112124  List<Failure> failures = overview.getFailures();
    113125  if (failures == null) failures = new LinkedList<Failure>();
     
    143155  }
    144156  </script>
     157  <style>
     158  .subtype, .subtype .link {
     159    font-size: 10px;
     160    color: #777777;
     161  }
     162  </style>
    145163  </base:head>
    146164
     
    149167      <tr>
    150168        <td class="prompt">Path</td>
    151         <td><%=getPath(ID, node)%></td>
     169        <td><%=getPath(dc, ID, node)%></td>
    152170      </tr>
    153171      <%
     
    253271        <tr>
    254272          <td class="prompt"><%=node.getNodeType() == Node.Type.FOLDER ?
    255             "Folder" : item != null ? item.getType().toString() : "Item"%></td>
     273              "Folder" : item != null ? item.getType().toString() : "Item"%></td>
    256274          <td>
    257275            <%
     
    261279              <%=Base.getLink(ID, node.getTitle(), item.getType(),item.getId(), item.hasPermission(Permission.WRITE))%>
    262280              <%
     281              if (item instanceof Subtypable)
     282              {
     283                ItemSubtype subtype = ((Subtypable)item).getItemSubtype();
     284                if (subtype != null)
     285                {
     286                  %>
     287                  <span class="subtype">(<%=Base.getLinkedName(ID, subtype, false, true)%>)</span>
     288                  <%
     289                }
     290              }
    263291            }
    264292            else
  • trunk/www/common/overview/tree.jsp

    r5556 r5651  
    2828  import="net.sf.basedb.core.Annotation"
    2929  import="net.sf.basedb.core.AnnotationType"
     30  import="net.sf.basedb.core.ItemSubtype"
    3031  import="net.sf.basedb.core.Nameable"
     32  import="net.sf.basedb.core.Subtypable"
    3133  import="net.sf.basedb.core.ItemContext"
    3234  import="net.sf.basedb.core.Permission"
     
    131133      }
    132134    }
    133     int numChildren = child.getChildren() == null ?
    134       0 : child.getChildren().size();
     135    int numChildren = child.getChildren() == null ? 0 : child.getChildren().size();
     136    String subtitle = null;
     137    if (child.getNodeType() == Node.Type.FOLDER)
     138    {
     139      subtitle = child.getChildren() == null ? "0" : Integer.toString(child.getChildren().size());
     140    }
     141    else if (child.getItem() instanceof Subtypable)
     142    {
     143      try
     144      {
     145        ItemSubtype subtype = ((Subtypable)child.getItem(dc)).getItemSubtype();
     146        if (subtype != null) subtitle = subtype.getName();
     147      }
     148      catch (Throwable t)
     149      {}
     150    }
     151   
    135152    if (!child.isChildrenLoaded())
    136153    {
     
    138155      sb.append(",'").append(folderIcon).append("'");
    139156      sb.append(",'").append(HTML.javaScriptEncode(child.getTitle()));
    140       sb.append(child.getNodeType() == Node.Type.FOLDER ? " (" + numChildren + ")" : "").append("',");
     157      sb.append(subtitle != null ? " <span class=\"subtitle\">(" + subtitle + ")</span>" : "").append("',");
    141158      sb.append("'showInfo(\"").append(child.getId()).append("\")','").append(HTML.javaScriptEncode(tooltip)).append("', '").append(child.getId()).append("',");
    142159      sb.append("'lazyInitSubNode(\"").append(child.getId()).append("\")')\n");
     
    145162    {
    146163       sb.append("var node").append(child.hashCode()).append(" = JoustMenu.addChildItem(").append("node"+startNode.hashCode());
    147              sb.append(",'").append(folderIcon).append("'");
    148              sb.append(",'").append(HTML.javaScriptEncode(child.getTitle()));
    149              sb.append(child.getNodeType() == Node.Type.FOLDER ? " (" + numChildren + ")" : "").append("',");
    150              sb.append("'showInfo(\"").append(child.getId()).append("\")','").append(HTML.javaScriptEncode(tooltip)).append("', '").append(child.getId()).append("')\n");
     164          sb.append(",'").append(folderIcon).append("'");
     165          sb.append(",'").append(HTML.javaScriptEncode(child.getTitle()));
     166          sb.append(subtitle != null ? " <span class=\"subtitle\">(" + subtitle + ")</span>" : "").append("',");
     167          sb.append("'showInfo(\"").append(child.getId()).append("\")','").append(HTML.javaScriptEncode(tooltip)).append("', '").append(child.getId()).append("')\n");
    151168    }
    152169    sb.append(generateSubTree(dc, child, ID, showFailures));
     
    164181  GenericOverview overview = OverviewUtil.getCurrentOverview(sc);
    165182  Boolean showFailures = Values.getBoolean(request.getParameter("show_failures"), false);
    166   Nameable rootItem = (Nameable)overview.getRootItem();
    167183  Node rootNode = overview.getRootNode();
     184  Nameable rootItem = (Nameable)rootNode.getItem(dc);
     185  String subtitle = null;
     186  if (rootItem instanceof Subtypable)
     187  {
     188    try
     189    {
     190      ItemSubtype subtype = ((Subtypable)rootItem).getItemSubtype();
     191      if (subtype != null) subtitle = subtype.getName();
     192    }
     193    catch (Throwable t)
     194    {}
     195  }
    168196  String rootIcon = "Home";
    169197  if (showFailures)
     
    229257    IconStore.addIcon('AnnotationChildError', path + 'annotationchilderror.gif', 18, 16);
    230258    IconStore.addIcon('AnnotatioChildnErrorSelected', path + 'annotationchilderrorselected.gif', 18, 16);
    231     var node<%=rootNode.hashCode()%> = JoustMenu.addMenuItem(-1, '<%=rootIcon%>', '<%=HTML.javaScriptEncode(rootItem.getName())%>', 'showInfo("<%=rootNode.getId()%>")', '', '<%=rootNode.getId()%>');
     259    var node<%=rootNode.hashCode()%> = JoustMenu.addMenuItem(-1, '<%=rootIcon%>', '<%=HTML.javaScriptEncode(rootItem.getName())%><%=subtitle != null ? " <span class=\"subtitle\">(" + subtitle + ")</span>" : ""%>', 'showInfo("<%=rootNode.getId()%>")', '', '<%=rootNode.getId()%>');
    232260    <%=generateSubTree(dc, rootNode, ID, showFailures)%>
    233261    JoustMenu.menuItems[node<%=rootNode.hashCode()%>].isOpen = true;
     
    298326 
    299327  </script>
     328  <style>
     329  .subtitle {
     330    font-size: 10px;
     331    color: #777777;
     332  }
     333  .selected .subtitle {
     334    color: #D0D0D0;
     335  }
     336  </style>
     337 
    300338  </base:head>
    301339    <base:body onload="initialise()">
Note: See TracChangeset for help on using the changeset viewer.