implicit TableHelper with 2.12.1? - phantom-dsl

Am I completely missing something? Trying to build the absolute most basic project with phantom is causing this error:
could not find implicit value for parameter helper: com.outworkers.phantom.macros.TableHelper[models.Accounts,models.Account]
build.sbt is using version 2.12.1.
Account.scala is this:
package models
import com.outworkers.phantom.dsl._
case class Account(username: String)
abstract class Accounts extends Table[Accounts, Account] with RootConnector {
object username extends StringColumn with PrimaryKey
}
I thought I was following the quickstart documentation, but I cannot get this to compile at all. Meanwhile, the Play-Cassandra project compiles just fine.

Writing here for future Googlers, this is because your schema does not define a PartitionKey, which is a requirement. The compiler should issue a warning when the macro is summoned.
package models
import com.outworkers.phantom.dsl._
case class Account(username: String)
abstract class Accounts extends Table[Accounts, Account] {
object username extends StringColumn with PartitionKey
}
On a side note, extending Table already brings in RootConnector, so you do not need to explicitly extend it again, as it was the case in older versions of phantom using CassandraTable instead of Table.

Related

How to import a class from a Jenkins Shared Library into the pipeline

I was using some global methods in the /var directory of the shared library, and everything worked fine. Now I need to keep the state of the process, so I'm writting a groovy class.
Basically I have a class called 'ClassTest.groovy' in '/src' which is something like this;
class ClassTest {
String testString
def method1() { ... }
def method2() { ... }
}
and at the begining of the pipeline
library 'testlibrary#'
import ClassTest
with result:
WorkflowScript: 2: unable to resolve class ClassTest #line 2, column 1.
import ClassTest
before, I was just goind
library 'testlibrary#' _
and using the methods as
script {
libraryTest.method1()
...
libraryTest.method2()
}
where the methods were in a file '/var/libraryTest.groovy' and everything worked. So I know that the shared library is there, but I'm confused with the way groovy / Jenkins handle classes / shared libraries.
What's the correct way to import a class? I cannot find a simple example (with groovy file, file structure and pipeline) in the documentation.
EDIT:
I moved the file to 'src/com/company/ClassTest.groovy' and modified the pipeline as
#Library('testlibrary#') import com.company.ClassTest
def notification = new ClassTest()
but now the error is
unexpected token: package # line 2
the first two lines of the groovy file are:
// src/com/company/ClassTest.groovy
package com.company;
So far this is what I've found.
To load the library in the pipeline I used:
#Library('testlibrary#') import com.company.ClassTest
def notification = new ClassTest()
In the class file, no package instruction. I guess that I don't need one because I don't have any other files or classes, so I don't really need a package. Also, I got an error when using the same name for the class and for the file where the class is. The error specifically complained and asked for one of them to be changed. I guess this two things are related to Jenkins.
That works, and the library is loaded.
(Maybe it can help someone else)
I was having the same issue.
Once I added a package-info.java inside the folder com/lib/, containing
/**
* com.lib package
*/
package com.lib;
and adding package com.lib at the first line of each file, it started to work.
I had the same problem.
After some trial and error with the docs of Jenkins.(https://www.jenkins.io/doc/book/pipeline/shared-libraries/#using-libraries)
I found that when I wanted to import a class from the shared library I have, I needed to do it like this:
//thanks to '_', the classes are imported automatically.
// MUST have the '#' at the beginning, other wise it will not work.
#Library('my-shared-library#BRANCH') _
// only by calling them you can tell if they exist or not.
def exampleObject = new example.GlobalVars()
// then call methods or attributes from the class.
exampleObject.runExample()

'FromHeaderAttribute' is not an attribute class

Having pulled this codebase:
https://github.com/RedRiverSoftware/FromHeaderAttribute
after reading this:
https://river.red/binding-to-and-validating-http-headers-with-web-api-2/
I am trying to change this:
public IHttpActionResult EchoHeaders([RedRiver.FromHead.FromHeader]StandardHeaders headers)
to this:
public IHttpActionResult EchoHeaders([FromHeader]StandardHeaders headers)
Obviously, I needed to add this to the top of the controller class:
using FromHeaderAttribute.Sample.Models;
But I am getting this error:
'FromHeaderAttribute' is not an attribute class.
However, looking at the code (which I have not changed) the 'FromHeaderAttribute' class clearly inherits 'ParameterBindingAttribute' which inherits 'System.Attribute'.
What am I missing to be able to define attributes which can be used as parameter attributes without specifying their whole namespace - just like attributes such as 'FromUri' and 'FromBody'?
Turns out that naming a class 'FromHeader' and trying to use it as a parameter attribute will not get recognised. I've tried this with a number of different combinations of file, class and namespace names and it just doesn't work. The attribute class name must be anything except FromHeader.

Composer package - use custom model if exists

My apologies if this exists already but my search-fu can not find the answer.
I have a composer package, and want to use my model ONLY IF an existing model doesn't exist (or extend the custom model), but I can't seem to figure out how to specify the "use" command properly inside my composer model. Since I won't know the name of the "app" using the package, I can't extend it.
<?php
namespace MyComposer\Package\Models;
use Illuminate\Database\Eloquent\Model;
class MyPackageModel extends Model
{
If I put it as a config option, I can't use that in the extends i.e class MyPackageModel extends config('custom_model_name')
I had thought I should do the check in the ServiceProvider but I can't seem to find the right code to register the proper model name to use in there.
Thanks.
I've done something similar to this before, I believe. But my approach was slightly different. See if it makes sense:
Create a base class in your own package. This will be the fallback
model which will be used if the "local" package (the one consuming
your package) doesn't have it's own version of it;
Create a config file which states which model will be used. The default is the model inside your own package (i.e. the fallback);
After installing and setting up your package, if a user does nothing they will automatically have your base model available. If they wish to override your base model with a custom local version, they can simply extend your base model and alter the model to be used in their config file.
I've also found that sometimes it's useful for the base model to 1) implement an interface that can be checked in your package's logic without relying on a specific class (which, after all, is meant to be overridden, right?); and 2) have most of it's logic inside a trait which the "local" model can use without ever having to extend your model (crucial if the local model already extends some other class for whatever reason).
How you approach the code would very much depend what you plan to do with that model. Say, for example, you have a supporting class that creates media entries in your database. Here's your packages model:
<?php
namespace Namespace\Package;
class Media
{
//...
}
And here's the default config:
<?php
return [
'model' => \Namespace\Package\Media::class,
];
And here's a sample manipulation, where you actually account for the local app to override your own model:
<?php
namespace Namespace\Package;
class MediaManager
{
protected function getModel()
{
$model = config('package.model');
return new $model;
}
public function createMedia($attributes = [])
{
$media = $this->getModel($attributes);
$media->save();
return $media;
}
}
That is to say, you never reference any Media model literally. You do your manipulations via the MediaManager. Of course the logic is very simplistic, but hopefully it's enough to get the bigger picture.

Use a class in two different project : decoder exception

I have an exception using this code ;
let readingData = NSKeyedUnarchiver.unarchiveObjectWithData(data) as? [ExternalProjectClass]
The message in the console :
cannot decode object of class (MyIOSApp.ExternalProjectClass) for key (NS.objects); the class may be defined in source code or a library that is not linked'
I use 'ExternalProjectClass' class in 2 project in the same workplace. In MyApp application (mac version). Otherwise I can use my class normally, I only have problems with coding.
I know how poor is my english. I hope somebody can help me.
Regards.
Swift class names have namespaces, and the default namespace is module name. So if you move the archive from an app to another, the class name differs.
You could put #objc(ExternalProjectClass) attribute on your class, so it is called ExternalProjectClass as far as NSCoder considers.
#objc(ExternalProjectClass) class ExternalProjectClass: NSObject, NSCoding { ... }

Declare a global variable in boo

As far as I can tell from the website, the following code should compile to a DLL with a top-level property Version:
namespace MyLibrary
[Module]
class MainClass:
public static Version as string
static def constructor():
Version = "0.1"
This compiles, but if I then enter these commands into booish:
import MyLibrary
print (Version)
then I get "ERROR: Unknown identifier: 'Version'".
Presumably this code worked in an earlier version of the language. I am using 0.9.4.9. What is the correct way to achieve this effect?
(I've noticed that there is an implicit static class MyVersionModule in which top-level static methods get placed, but I don't know how to add properties to this either).
In .net there is no way to have methods or fields that are not actually members of a class. Boo hides this somewhat by having the implicit class for the main file in the module (as you noticed) but when importing you still need to access it as a member.
For statics you have to first reference the type then the member so in your example printing the version would be like this:
import MyLibrary
print (MainClass.Version)
Of course this isn't the 'correct' way to store version information in .net though, which is to use assembly level attributes instead. That would look more like this:
[assembly: System.Reflection.AssemblyVersion("1.0")]
namespace MyLibrary
[Module]
class MainClass:
pass
Then getting the version you would do using reflection, there are a couple of ways to get the assembly but the easiest is to get the Type then it's assembly:
import System
import System.Reflection
import MyLibrary
atts = typeof(MainClass).Assembly \
.GetCustomAttributes(typeof(AssemblyVersionAttribute), false)
version = (atts[0] as AssemblyVersionAttribute).Version
print(version)

Resources