After an evaluation, GNOME has moved from Bugzilla to GitLab. Learn more about GitLab.
No new issues can be reported in GNOME Bugzilla anymore.
To report an issue in a GNOME project, go to GNOME GitLab.
Do not go to GNOME Gitlab for: Bluefish, Doxygen, GnuCash, GStreamer, java-gnome, LDTP, NetworkManager, Tomboy.
Bug 607568 - Properties not supported in compact classes, but vala showing an unrelated error
Properties not supported in compact classes, but vala showing an unrelated error
Status: RESOLVED FIXED
Product: vala
Classification: Core
Component: Objects
unspecified
Other All
: Normal normal
: ---
Assigned To: Vala maintainers
Vala maintainers
Depends on:
Blocks: 792254
 
 
Reported: 2010-01-20 16:42 UTC by pancake
Modified: 2018-01-05 21:19 UTC
See Also:
GNOME target: ---
GNOME version: ---


Attachments
Fix auto properties getter/setter on compact classes (3.20 KB, patch)
2010-01-20 22:28 UTC, Marc-Andre Lureau
rejected Details | Review

Description pancake 2010-01-20 16:42:33 UTC
When trying to compile properties in compact classes you get:

  test.vala:2.1-2.16: error: Private fields not supported in compact classes

I think that properties should be supported for compact classes as well as in GObject based ones (this should be another bug). But the error message should be more descriptive if it is really not going to be supported.

This should probably happen in other special types like signal or private data.

test code is:

---------8<--------------
[Compact]
public class Foo {
        public string name { get; set; }

        public Foo (string name) {
                this.name = name;
        }
}

void main() {
        Foo foo = new Foo ("foo");
        foo = null;
}
-------------->8---------
Comment 1 zarevucky.jiri 2010-01-20 18:52:49 UTC
Actually, the error is correct. Properties are supported for compact classes, but automatic property creates a private variable to store the value, which isn't supported.
Comment 2 zarevucky.jiri 2010-01-20 19:03:14 UTC
Though the error is not obvious and should read something like "Automatic properties not supported for compact classes", I'd be more interested in generally allowing private fields there. Why is it not possible?
Comment 3 Marc-Andre Lureau 2010-01-20 22:28:43 UTC
Created attachment 151880 [details] [review]
Fix auto properties getter/setter on compact classes

Fixes
Comment 4 Jürg Billeter 2010-03-20 12:02:41 UTC
Private fields are not possible as Vala does not add implicit fields such as 'priv' to the struct of a compact class. They are only meant to be used for bindings and few other special cases.

I don't see a point in allowing automatic properties here. They are nearly equivalent to public fields, but the fact that you expose a struct field / change the API/ABI is hidden. If anyone thinks there is a use case for this, please comment, otherwise we should just improve the error message.
Comment 5 Michael 'Mickey' Lauer 2011-03-03 15:34:23 UTC
I agree with that. Compact classes can use public attributes.
Comment 6 Daniel Espinosa 2018-01-05 21:19:23 UTC
Taking following code:

[Compact]
public class Test {
	public string name;
	public string id { get { return name; } set { name = value; } }
}

public void main () {
	var c = new Test ();
	c.id = "Name";
	stdout.printf (c.id);
}

Compact classes' property declaration can be used to declare accessors for a C struct members in the way programmers want their C users do it.

Using valac -H to create a header, you will find:

typedef struct _Test Test;

struct _Test {
	gchar* name;
};


void test_free (Test* self);
Test* test_new (void);
const gchar* test_get_id (Test* self);
void test_set_id (Test* self, const gchar* value);
void _vala_main (void);


So your C API users can use test_get/set_id() to access your compact class (C struct) members.

If you, the author, don't want to expose your struct's members to the public API, you can declare as "internal":

[Compact]
internal class Test {
	public string name;
}

[Compact]
public class PublicTest {
	internal Test test;
	public PublicTest (string n) {
		test = new Test ();
		test.name = n;
	}
	public string id { get { return test.name; } set { test.name = value; } }
}

Your header file will be:

typedef struct _PublicTest PublicTest;
typedef struct _Test Test;

struct _PublicTest {
	Test* test;
};


void public_test_free (PublicTest* self);
void test_free (Test* self);
PublicTest* public_test_new (const gchar* n);
const gchar* public_test_get_id (PublicTest* self);
void public_test_set_id (PublicTest* self, const gchar* value);
void _vala_main (void);

As you can see your Test struct is now sealed and no one can access it, but with PublicTest API exposed.

Because this is not a problem for Vala and already rised error for private files not supported, I'm closing this bug for further discussion on bug:

https://bugzilla.gnome.org/show_bug.cgi?id=792254